/* global React, I, UI, SSSData */
const { useState: useStateN, useMemo: useMemoN, useEffect: useEffectN } = React;
const { Btn, Badge, Card, Drawer, Workflow } = window.UI;
const { fmtM, fmt0, bahtText } = window.UI;

// =============== เก็บเอกสารที่สร้างจริง (persist + apply เข้า SSSData) ===============
const NDC_KEY = "sss-created-docs";
function ndcLoad() { try { return JSON.parse(localStorage.getItem(NDC_KEY) || "{}"); } catch { return {}; } }
window.DocCreateStore = {
  add(listKey, row) {
    const m = ndcLoad();
    m[listKey] = (m[listKey] || []).filter(r => r.no !== row.no);
    m[listKey].unshift(row);
    try { localStorage.setItem(NDC_KEY, JSON.stringify(m)); } catch {}
    const list = window.SSSData[listKey] = window.SSSData[listKey] || [];
    const idx = list.findIndex(r => r.no === row.no);
    if (idx >= 0) list[idx] = { ...list[idx], ...row }; else list.unshift(row);
    window.dispatchEvent(new Event("sss-docs-changed"));
  },
  apply() {
    const m = ndcLoad();
    Object.entries(m).forEach(([lk, rows]) => {
      const list = window.SSSData[lk] = window.SSSData[lk] || [];
      rows.forEach(row => { if (!list.some(r => r.no === row.no)) list.unshift(row); });
    });
  }
};
window.DocCreateStore.apply();
const NDC_DEFAULT_STATUS = { quotation: "ร่าง", invoice: "ค้างชำระ", "delivery-note": "กำลังจัดส่ง", "tax-invoice": "เต็มรูป", "billing-note": "ส่งแล้ว", receipt: "ออกแล้ว", "purchase-order": "รออนุมัติ", "payment-voucher": "รอจ่าย" };
const NDC_ROUTE = { quotation: "quotations", invoice: "invoices", "delivery-note": "delivery-notes", "tax-invoice": "tax-invoices", "billing-note": "billing-notes", receipt: "receipts", "purchase-order": "purchase-orders", "payment-voucher": "payment-vouchers" };

// =============== หมายเหตุเอกสารสำเร็จรูป (ตั้งค่าได้) ===============
const NDN_KEY = "sss-doc-note-presets";
const NDN_DEFAULTS = [
  "• ราคาข้างต้นเป็นราคาก่อนภาษีมูลค่าเพิ่ม",
  "• ระยะเวลาผลิตประมาณ 25-30 วันทำการ หลังได้รับ PO + เงินมัดจำ 50%",
  "• ชำระมัดจำ 50% ส่วนที่เหลือก่อนส่งงาน",
  "• ยืนราคา 30 วันนับจากวันที่ในเอกสาร",
  "• กรุณาชำระเงินภายในกำหนด · โอนเข้าบัญชีบริษัทเท่านั้น",
  "• สินค้ารับประกัน 1 ปี ตามเงื่อนไขบริษัท",
  "• แบบ 3D ที่ส่งให้ลูกค้าถือเป็นทรัพย์สินของบริษัทจนกว่าจะชำระครบ"
];
window.DocNotePresets = {
  load() { try { return JSON.parse(localStorage.getItem(NDN_KEY) || "null") || NDN_DEFAULTS; } catch { return NDN_DEFAULTS; } },
  save(list) { try { localStorage.setItem(NDN_KEY, JSON.stringify(list)); } catch {} window.dispatchEvent(new Event("sss-note-presets-changed")); },
  DEFAULTS: NDN_DEFAULTS
};

// =============== Document type config ===============
const DOC_TYPES = {
  quotation: {
    title: "ใบเสนอราคา",
    titleEn: "QUOTATION",
    prefix: "QO",
    next: "QO-2569-0118",
    party: "customer",
    partyLabel: "ลูกค้า",
    showDue: false,
    showValidity: true,
    showVAT: true,
    showSign: ["ผู้เสนอราคา", "ลูกค้าอนุมัติ"],
    listKey: "Quotations",
    note: "• ราคาข้างต้นเป็นราคาก่อนภาษีมูลค่าเพิ่ม\n• ระยะเวลาผลิตประมาณ 25-30 วันทำการ\n• ชำระมัดจำ 50% ส่วนที่เหลือก่อนส่งงาน"
  },
  "delivery-note": {
    title: "ใบส่งสินค้า",
    titleEn: "DELIVERY NOTE",
    prefix: "DN",
    next: "DN-2569-0189",
    party: "customer",
    partyLabel: "ผู้รับสินค้า",
    showDue: false,
    showVAT: false,
    showQty: true,
    showSign: ["ผู้ส่งของ", "ผู้รับของ", "วันที่/เวลารับ"],
    listKey: "DeliveryNotes",
    note: "โปรดตรวจรับสินค้าให้ครบถ้วนก่อนเซ็นรับ หากชำรุดเสียหายแจ้งทันที"
  },
  invoice: {
    title: "ใบส่งสินค้า / ใบแจ้งหนี้",
    titleEn: "DELIVERY NOTE / INVOICE",
    prefix: "INV",
    next: "INV-2569-0205",
    party: "customer",
    partyLabel: "ลูกค้า",
    showDue: true,
    showVAT: true,
    showSign: ["ผู้วางบิล", "ผู้รับวางบิล"],
    listKey: "Invoices",
    note: "กรุณาชำระเงินภายในกำหนด · โอนเข้าบัญชี ธ.ไทยพาณิชย์ 4211849819"
  },
  "tax-invoice": {
    title: "ใบกำกับภาษี",
    titleEn: "TAX INVOICE",
    prefix: "TX",
    next: "TX-2569-0205",
    party: "customer",
    partyLabel: "ลูกค้า (ผู้ซื้อ)",
    showDue: false,
    showVAT: true,
    showFullVAT: true,
    showSign: ["ผู้มีอำนาจลงนาม"],
    listKey: "TaxInvoices",
    note: "เอกสารฉบับนี้เป็นใบกำกับภาษีตามประมวลรัษฎากรมาตรา 86"
  },
  "billing-note": {
    title: "ใบวางบิล",
    titleEn: "BILLING NOTE",
    prefix: "BN",
    next: "BN-2569-0045",
    party: "customer",
    partyLabel: "ลูกค้า",
    showDue: true,
    showVAT: false,
    showSign: ["ผู้วางบิล", "ผู้รับวางบิล"],
    listKey: "BillingNotes",
    note: "กรุณานัดวันเก็บเงิน · ทุกวันอังคาร-พฤหัส 9.00-16.00 น."
  },
  receipt: {
    title: "ใบเสร็จรับเงิน",
    titleEn: "OFFICIAL RECEIPT",
    prefix: "RC",
    next: "RC-2569-0157",
    party: "customer",
    partyLabel: "ได้รับเงินจาก",
    showDue: false,
    showVAT: true,
    showStamp: true,
    showMethod: true,
    showSign: ["ผู้รับเงิน", "ตราประทับ"],
    listKey: "Receipts",
    note: "ได้รับเงินครบถ้วนเรียบร้อยแล้ว · ขอบคุณที่ใช้บริการ"
  },
  "purchase-order": {
    title: "ใบสั่งซื้อ",
    titleEn: "PURCHASE ORDER",
    prefix: "PO",
    next: "PO-2569-0099",
    party: "vendor",
    partyLabel: "ผู้ขาย",
    showDue: false,
    showExpected: true,
    showVAT: true,
    showSign: ["ผู้สั่งซื้อ", "ผู้รับใบสั่งซื้อ"],
    listKey: "PurchaseOrders",
    note: "กรุณายืนยันคำสั่งซื้อภายใน 24 ชม. · ระบุวันส่งสินค้าให้ชัดเจน"
  },
  "payment-voucher": {
    title: "ใบสำคัญจ่าย",
    titleEn: "PAYMENT VOUCHER",
    prefix: "PV",
    next: "PV-2569-0079",
    party: "vendor",
    partyLabel: "จ่ายให้",
    showDue: false,
    showMethod: true,
    showVAT: false,
    showSign: ["ผู้จัดทำ", "ผู้อนุมัติ", "ผู้รับเงิน"],
    listKey: "PaymentVouchers",
    note: "เอกสารฉบับนี้เป็นหลักฐานการจ่ายเงิน"
  }
};

// =============== Searchable party combobox ===============
function PartyCombo({ list, value, onChange }) {
  const [open, setOpen] = useStateN(false);
  const [q, setQ] = useStateN("");
  const sel = list.find(p => p.id === value);
  const ql = q.trim().toLowerCase();
  const filtered = ql ? list.filter(p => (p.id + " " + p.name + " " + (p.contact || "") + " " + (p.phone || "") + " " + (p.taxId || "")).toLowerCase().includes(ql)) : list;
  return (
    <div style={{position: "relative"}}>
      <div style={{position: "relative"}}>
        <input className="input" style={{paddingRight: 30}}
          value={open ? q : (sel ? `${sel.id} — ${sel.name}` : "")}
          placeholder="พิมพ์ค้นหาชื่อ / รหัส / เบอร์โทร…"
          onFocus={() => { setOpen(true); setQ(""); }}
          onChange={e => { setQ(e.target.value); setOpen(true); }}
          onBlur={() => setTimeout(() => setOpen(false), 150)}
          onKeyDown={e => {
            if (e.key === "Enter" && filtered.length > 0) { onChange(filtered[0].id); setOpen(false); e.target.blur(); }
            if (e.key === "Escape") { setOpen(false); e.target.blur(); }
          }}
        ></input>
        <span style={{position: "absolute", right: 10, top: "50%", transform: "translateY(-50%)", color: "var(--ink-3)", pointerEvents: "none", display: "flex"}}>
          {open ? <I.search size={13}/> : <I.chevronDown size={13}/>}
        </span>
      </div>
      {open && (
        <div style={{position: "absolute", top: "100%", left: 0, right: 0, zIndex: 70, background: "var(--surface)", border: "1px solid var(--line)", borderRadius: 8, boxShadow: "var(--shadow-lg)", maxHeight: 280, overflowY: "auto", marginTop: 4}}>
          {filtered.map(p => (
            <div key={p.id}
              onMouseDown={(e) => { e.preventDefault(); onChange(p.id); setOpen(false); }}
              style={{padding: "8px 12px", cursor: "pointer", borderBottom: "1px solid var(--line-soft)", background: p.id === value ? "var(--surface-2)" : "transparent"}}
              onMouseEnter={e => e.currentTarget.style.background = "var(--surface-2)"}
              onMouseLeave={e => e.currentTarget.style.background = p.id === value ? "var(--surface-2)" : "transparent"}>
              <div style={{fontSize: 12.5, fontWeight: 500}}><span className="mono" style={{fontSize: 11, color: "var(--ink-3)"}}>{p.id}</span> — {p.name}</div>
              <div style={{fontSize: 11, color: "var(--ink-3)", marginTop: 1}}>{p.contact}{p.phone ? <span className="mono"> · {p.phone}</span> : null}</div>
            </div>
          ))}
          {filtered.length === 0 && <div style={{padding: 14, fontSize: 12, color: "var(--ink-3)", textAlign: "center"}}>ไม่พบ "{q}"</div>}
        </div>
      )}
    </div>
  );
}

// =============== Main create-doc drawer ===============
function NewDocDrawer({ docType, onClose, prefill }) {
  const D = window.SSSData;
  const cfg = DOC_TYPES[docType] || DOC_TYPES.quotation;
  const partyList = cfg.party === "customer" ? D.Customers : D.Vendors;

  const today = "22 พ.ค. 2569";
  const [docNo, setDocNo] = useStateN(prefill && prefill.docNo ? prefill.docNo : cfg.next);
  const [date, setDate] = useStateN(today);
  const [dueDate, setDueDate] = useStateN("21 มิ.ย. 2569");
  const [validity, setValidity] = useStateN("30 วัน");
  const [partyId, setPartyId] = useStateN(() => prefill && prefill.partyName ? ((partyList.find(p => p.name === prefill.partyName) || partyList[0]).id) : partyList[0].id);
  const [lines, setLines] = useStateN(() => prefill && prefill.lines && prefill.lines.length
    ? prefill.lines.map((l, i) => ({ id: i + 1, sku: l.sku || "", name: l.name || "", qty: l.qty || 1, unit: l.unit || "ชิ้น", price: l.price || 0, img: l.img || "" }))
    : [{ id: 1, sku: "", name: "", qty: 1, unit: "ชิ้น", price: 0 }]
  );
  const [discount, setDiscount] = useStateN(0);
  const [vatPct, setVatPct] = useStateN(cfg.showVAT ? 7 : 0);
  const [notes, setNotes] = useStateN(prefill && prefill.notes ? prefill.notes : cfg.note);
  // วิธีรับ/จ่ายเงินจริง — อิงจากบัญชีธนาคารที่มีจริง + เช็ค/หักบัญชี
const PAY_METHODS = (() => {
    const accs = (window.CompanyCashStore && window.CompanyCashStore.ACCOUNTS) || [];
    const out = [];
    accs.forEach(a => out.push(a.kind === "เงินสด" ? `💵 เงินสด` : `🏦 โอน · ${a.short}`));
    out.push("🧾 เช็ค", "🔁 หักบัญชีอัตโนมัติ");
    return out;
  })();
  const [method, setMethod] = useStateN(PAY_METHODS[0] || "💵 เงินสด");
  const [taxType, setTaxType] = useStateN("เต็มรูป"); // ใบกำกับภาษี: เต็มรูป / อย่างย่อ
  const [expected, setExpected] = useStateN("29 พ.ค. 2569");
  const [showPrint, setShowPrint] = useStateN(false);
  // ใบเสนอราคาแบบมีรูปในรายการ (ติ๊กเพื่อแนบรูปต่อรายการ)
  const canImages = docType === "quotation";
  const [withImages, setWithImages] = useStateN(() => !!(prefill && prefill.withImages));

  const pickLineImg = async (id, file) => {
    if (!file) return;
    const dataUrl = window.DeliveryStore && window.DeliveryStore.resizeImage
      ? await window.DeliveryStore.resizeImage(file, 500) : null;
    if (dataUrl) updLine(id, { img: dataUrl });
    else window.toast && window.toast("อ่านรูปไม่สำเร็จ ลองใหม่");
  };

  const party = partyList.find(p => p.id === partyId);

  // ✅ ใบวางบิล: ออกจากใบแจ้งหนี้เท่านั้น — เลือกรายการเอกสารแทนสินค้า
  const isBilling = docType === "billing-note";
  const [selInv, setSelInv] = useStateN([]);
  const [printCopies, setPrintCopies] = useStateN(true);
  const custInvoices = isBilling ? (D.Invoices || []).filter(i => i.customer === (party && party.name) && i.status !== "ชำระแล้ว") : [];
  const billLines = selInv.map((no, i) => { const inv = (D.Invoices || []).find(x => x.no === no); const owed = inv ? (inv.amount - (inv.paid || 0)) : 0; return { id: i + 1, sku: "", name: `ใบแจ้งหนี้ ${no}${inv ? " · " + inv.date : ""}`, qty: 1, unit: "ใบ", price: owed, _inv: inv }; });
  const effLines = isBilling ? billLines : lines;
  const toggleInv = (no) => setSelInv(s => s.includes(no) ? s.filter(x => x !== no) : [...s, no]);

  const subtotal = useMemoN(() => effLines.reduce((s, l) => s + (Number(l.qty) || 0) * (Number(l.price) || 0), 0), [effLines]);
  const afterDisc = subtotal - Number(discount || 0);
  const vat = cfg.showVAT ? afterDisc * (Number(vatPct) || 0) / 100 : 0;
  const grand = afterDisc + vat;

  const addLine = () => setLines(ls => [...ls, { id: Date.now(), sku: "", name: "", qty: 1, unit: "ชิ้น", price: 0 }]);
  const delLine = (id) => setLines(ls => ls.length > 1 ? ls.filter(l => l.id !== id) : ls);
  const updLine = (id, patch) => setLines(ls => ls.map(l => l.id === id ? { ...l, ...patch } : l));
  const pickProduct = (id, sku) => {
    if (!sku) { updLine(id, { sku: "", name: "" }); return; }
    const p = D.Products.find(x => x.sku === sku);
    if (p) updLine(id, { sku: p.sku, name: p.name, unit: p.unit, price: cfg.party === "vendor" ? p.cost : p.price });
  };

  const save = () => {
    if (isBilling && selInv.length === 0) { window.toast && window.toast("เลือกใบแจ้งหนี้ที่จะนำมาวางบิลอย่างน้อย 1 ใบ"); return; }
    if (!party) { window.toast && window.toast("เลือก" + cfg.partyLabel + "ก่อน"); return; }
    // ✅ สร้างเอกสารจริง + บันทึกถาวร
    const row = { no: docNo, date, amount: Math.round(grand), status: NDC_DEFAULT_STATUS[docType] || "ออกแล้ว" };
    if (cfg.party === "customer") row.customer = party.name;
    else if (docType === "payment-voucher") row.payee = party.name;
    else row.vendor = party.name;
    if (cfg.showDue) row.due = dueDate;
    if (cfg.showValidity) row.validity = validity;
    if (docType === "invoice") row.paid = 0;
    if (docType === "tax-invoice") row.type = taxType;
    if (cfg.showMethod) row.method = method;
    if (isBilling) row.invoices = selInv.slice();
    // เก็บรายการ + รูป (ใบเสนอราคา) เพื่อพิมพ์ซ้ำภายหลัง
    if (!isBilling) {
      row.lines = lines.map(l => ({ sku: l.sku, name: l.name, qty: l.qty, unit: l.unit, price: l.price, ...(l.img ? { img: l.img } : {}) }));
      if (canImages) row.withImages = withImages;
    }
    window.DocCreateStore.add(cfg.listKey, row);
    window.logActivity && window.logActivity(prefill && prefill.editing ? "แก้ไขเอกสาร" : "สร้างเอกสาร", `${cfg.title} ${docNo} · ฿${fmtM(grand)}`, "create");
    window.toast && window.toast(`บันทึก ${cfg.title} ${docNo} แล้ว${isBilling && printCopies ? " · แนบสำเนาใบแจ้งหนี้แล้ว" : ""} — เปิดดูได้ในรายการ`);
    onClose && onClose();
    const route = NDC_ROUTE[docType];
    if (route) setTimeout(() => { window.location.hash = "#/" + route; }, 250);
  };
  const saveAndPrint = () => {
    if (isBilling && selInv.length === 0) { window.toast && window.toast("เลือกใบแจ้งหนี้ที่จะนำมาวางบิลอย่างน้อย 1 ใบ"); return; }
    setShowPrint(true);
    if (isBilling && printCopies) window.__billCopies = selInv.slice();
    setTimeout(() => window.printDocPaperWithOptions(), 250);
  };
  // เตือนถ้ายังไม่ได้บันทึก
  const isDirty = () => (isBilling ? selInv.length > 0 : lines.some(l => l.name || (Number(l.qty) || 0) > 1 || (Number(l.price) || 0) > 0)) || (Number(discount) || 0) > 0 || notes !== cfg.note;
  const requestClose = async () => {
    if (isDirty()) {
      const ok = await window.confirmDialog({
        title: "ยังไม่ได้บันทึกเอกสาร",
        message: `มีการแก้ไขใน <b>${cfg.title} ${docNo}</b> ที่ยังไม่ได้บันทึก — ออกโดยไม่บันทึก?`,
        confirmText: "ออกโดยไม่บันทึก", cancelText: "กลับไปแก้ต่อ"
      });
      if (!ok) return;
    }
    onClose && onClose();
  };

  return (
    <>
      <div className="scrim" onClick={requestClose}/>
      <div className="drawer wide newdoc-drawer" style={{width: 1080}}>
        <div className="drawer-head">
          <I.plus size={16}/>
          <h3>{prefill && prefill.editing ? "แก้ไข" : "สร้าง"} {cfg.title}</h3>
          {prefill && prefill.fromDoc && <span className="badge info" style={{marginLeft: 8}}>📋 สร้างจาก {prefill.fromDoc} — ตรวจสอบแล้วกดบันทึก</span>}
          {prefill && prefill.editing && <span className="badge warning" style={{marginLeft: 8}}>✏️ แก้ไขเอกสาร {prefill.docNo}</span>}
          <span className="mono muted" style={{fontSize: 12}}>{docNo}</span>
          <span className="spacer"/>
          <button className="icon-btn" onClick={onClose}><I.close size={14}/></button>
        </div>
        <div className="drawer-body" style={{padding: 0, display: "grid", gridTemplateColumns: "1fr 1fr"}}>
          {/* LEFT: Form */}
          <div style={{padding: 18, borderRight: "1px solid var(--line)", overflowY: "auto"}}>
            <div className="h2 mb">ข้อมูลเอกสาร</div>
            <div className="field-row cols-2 mb">
              <div className="field"><label>เลขที่</label><input className="input mono" value={docNo} onChange={e=>setDocNo(e.target.value)}/></div>
              <div className="field"><label>วันที่ออก</label><input className="input" value={date} onChange={e=>setDate(e.target.value)}/></div>
            </div>
            {cfg.showDue && (
              <div className="field-row cols-2 mb">
                <div className="field"><label>ครบกำหนดชำระ</label><input className="input" value={dueDate} onChange={e=>setDueDate(e.target.value)}/></div>
                <div className="field"><label>เครดิต</label><div className="input" style={{display: "flex", alignItems: "center", color: "var(--ink-3)"}}>{party?.credit || 30} วัน (อัตโนมัติ)</div></div>
              </div>
            )}
            {cfg.showValidity && (
              <div className="field-row cols-2 mb">
                <div className="field"><label>ยืนราคา</label>
                  <select className="input" value={validity} onChange={e=>setValidity(e.target.value)}>
                    <option>7 วัน</option><option>15 วัน</option><option>30 วัน</option><option>60 วัน</option>
                  </select>
                </div>
                <div></div>
              </div>
            )}
            {cfg.showExpected && (
              <div className="field-row cols-2 mb">
                <div className="field"><label>นัดรับสินค้า</label><input className="input" value={expected} onChange={e=>setExpected(e.target.value)}/></div>
                <div></div>
              </div>
            )}
            {cfg.showMethod && (
              <div className="field-row cols-2 mb">
                <div className="field"><label>วิธีรับ/จ่ายเงิน</label>
                  <select className="input" value={method} onChange={e=>setMethod(e.target.value)}>
                    {PAY_METHODS.map(m => <option key={m} value={m}>{m}</option>)}
                  </select>
                </div>
                {docType === "tax-invoice"
                  ? <div className="field"><label>ประเภทใบกำกับภาษี</label>
                      <div className="payseg" style={{display: "flex"}}>
                        {["เต็มรูป", "อย่างย่อ"].map(tt => (
                          <button key={tt} type="button" className={"payseg-btn" + (taxType === tt ? " active" : "")} style={{flex: 1}} onClick={() => setTaxType(tt)}>{tt === "เต็มรูป" ? "เต็มรูปแบบ" : "อย่างย่อ"}</button>
                        ))}
                      </div>
                    </div>
                  : <div></div>}
              </div>
            )}

            <div className="h2 mt-lg mb">{cfg.partyLabel}</div>
            <div className="field mb">
              <PartyCombo list={partyList} value={partyId} onChange={setPartyId}/>
            </div>
            {party && (
              <div style={{padding: 10, background: "var(--surface-2)", borderRadius: 6, fontSize: 12, color: "var(--ink-3)", marginBottom: 12, lineHeight: 1.6}}>
                <div>{party.contact} · <span className="mono">{party.phone}</span></div>
                <div>เลขผู้เสียภาษี: <span className="mono">{party.taxId}</span></div>
                {party.credit && <div>เครดิต: {party.credit} วัน</div>}
              </div>
            )}

            <div className="h2 mt-lg mb" style={{display: "flex", alignItems: "center"}}>
              <span>{isBilling ? "เอกสารที่นำมาวางบิล" : "รายการสินค้า/บริการ"}</span>
              <span className="spacer"/>
              {!isBilling && <Btn size="sm" icon={I.plus} onClick={addLine}>เพิ่มรายการ</Btn>}
            </div>
            {canImages && (
              <label style={{display: "flex", alignItems: "center", gap: 8, fontSize: 12.5, cursor: "pointer", padding: "8px 12px", background: withImages ? "var(--surface-2)" : "transparent", border: withImages ? "1.5px solid var(--accent)" : "1px solid var(--line)", borderRadius: 8, marginBottom: 8}}>
                <input type="checkbox" checked={withImages} onChange={e => setWithImages(e.target.checked)}/>
                <span>🖼️ ใส่รูปภาพในรายการ — ออกใบเสนอราคาแบบมีรูปสินค้าต่อรายการ</span>
              </label>
            )}
            {isBilling ? (
              <div style={{display: "flex", flexDirection: "column", gap: 8}}>
                <div style={{fontSize: 12, color: "var(--ink-3)"}}>ใบวางบิลออกจาก"ใบส่งสินค้า/ใบแจ้งหนี้"ที่ยังไม่ชำระของลูกค้ารายนี้ — เลือกได้หลายใบ</div>
                {custInvoices.length === 0 && <div style={{padding: 16, textAlign: "center", color: "var(--ink-3)", fontSize: 12.5, border: "1px dashed var(--line)", borderRadius: 8}}>ลูกค้ารายนี้ไม่มีใบแจ้งหนี้ค้างชำระ — เลือกลูกค้ารายอื่น</div>}
                {custInvoices.map(inv => {
                  const owed = inv.amount - (inv.paid || 0);
                  const on = selInv.includes(inv.no);
                  return (
                    <label key={inv.no} style={{display: "flex", alignItems: "center", gap: 10, padding: "9px 12px", border: on ? "1.5px solid var(--accent)" : "1px solid var(--line)", borderRadius: 8, cursor: "pointer", background: on ? "var(--surface-2)" : "var(--surface)"}}>
                      <input type="checkbox" checked={on} onChange={() => toggleInv(inv.no)}></input>
                      <div style={{flex: 1, minWidth: 0}}>
                        <div style={{fontSize: 12.5, fontWeight: 600}}><span className="mono">{inv.no}</span> · {inv.date}</div>
                        <div style={{fontSize: 11, color: "var(--ink-3)"}}>ครบกำหนด {inv.due || "—"} · สถานะ {inv.status}</div>
                      </div>
                      <span className="amount" style={{fontWeight: 600, fontSize: 12.5}}>฿{fmtM(owed)}</span>
                    </label>
                  );
                })}
                <label style={{display: "flex", alignItems: "center", gap: 8, marginTop: 4, fontSize: 12.5, cursor: "pointer", padding: "8px 12px", background: "var(--surface-2)", borderRadius: 8}}>
                  <input type="checkbox" checked={printCopies} onChange={e => setPrintCopies(e.target.checked)}></input>
                  📎 พิมพ์สำเนาใบแจ้งหนี้ที่นำมาวางบิลแนบท้ายใบวางบิล ({selInv.length} ใบ)
                </label>
              </div>
            ) : (
            <div style={{display: "flex", flexDirection: "column", gap: 8}}>
              {lines.map((l, i) => (
                <div key={l.id} style={{padding: 10, border: "1px solid var(--line)", borderRadius: 8, background: "var(--surface)"}}>
                  <div style={{display: "flex", alignItems: "center", gap: 8, marginBottom: 8}}>
                    <span style={{fontSize: 11, color: "var(--ink-3)", width: 18}}>#{i + 1}</span>
                    <select className="input" style={{height: 30, flex: 1}} value={l.sku} onChange={e=>pickProduct(l.id, e.target.value)}>
                      <option value="">— เลือกจากคลัง หรือกรอกเอง —</option>
                      {D.Products.map(p => <option key={p.sku} value={p.sku}>{p.sku} — {p.name}</option>)}
                    </select>
                    <button className="icon-btn" onClick={() => delLine(l.id)} title="ลบ"><I.trash size={12}/></button>
                  </div>
                  <input className="input" style={{marginBottom: 6}} placeholder="ชื่อรายการ" value={l.name} onChange={e=>updLine(l.id, { name: e.target.value })}/>
                  <div style={{display: "grid", gridTemplateColumns: "1fr 1fr 1.2fr 1fr", gap: 6}}>
                    <input className="input" type="number" placeholder="จำนวน" value={l.qty} onChange={e=>updLine(l.id, { qty: e.target.value })}/>
                    <input className="input" placeholder="หน่วย" value={l.unit} onChange={e=>updLine(l.id, { unit: e.target.value })}/>
                    <input className="input" type="number" placeholder="ราคา/หน่วย" value={l.price} onChange={e=>updLine(l.id, { price: e.target.value })}/>
                    <div className="input amount" style={{display: "flex", alignItems: "center", justifyContent: "flex-end", background: "var(--surface-2)"}}>฿{fmtM((Number(l.qty)||0) * (Number(l.price)||0))}</div>
                  </div>
                  {canImages && withImages && (
                    <div style={{display: "flex", alignItems: "center", gap: 8, marginTop: 8}}>
                      {l.img
                        ? <img src={l.img} alt="" style={{width: 46, height: 46, objectFit: "cover", borderRadius: 6, border: "1px solid var(--line)"}}/>
                        : <div style={{width: 46, height: 46, borderRadius: 6, border: "1px dashed var(--line-strong)", display: "grid", placeItems: "center", color: "var(--ink-3)"}}><I.camera size={16}/></div>}
                      <label className="btn" style={{cursor: "pointer", fontSize: 12}}>
                        {l.img ? "เปลี่ยนรูป" : "แนบรูป"}
                        <input type="file" accept="image/*" style={{display: "none"}} onChange={e => pickLineImg(l.id, e.target.files && e.target.files[0])}/>
                      </label>
                      {l.img && <button className="icon-btn" title="ลบรูป" onClick={() => updLine(l.id, { img: "" })}><I.trash size={12}/></button>}
                    </div>
                  )}
                </div>
              ))}
            </div>
            )}

            <div className="h2 mt-lg mb">สรุปยอด</div>
            <div style={{display: "flex", flexDirection: "column", gap: 6, padding: 12, background: "var(--surface-2)", borderRadius: 8}}>
              <div style={{display: "flex", justifyContent: "space-between"}}><span className="muted">รวมเป็นเงิน</span><span className="amount">฿{fmtM(subtotal)}</span></div>
              <div style={{display: "flex", justifyContent: "space-between", alignItems: "center"}}>
                <span className="muted">ส่วนลด</span>
                <input className="input" type="number" value={discount} onChange={e=>setDiscount(e.target.value)} style={{width: 110, textAlign: "right", height: 26}}/>
              </div>
              {(cfg.showVAT || cfg.party === "customer") && (
                <div style={{display: "flex", justifyContent: "space-between", alignItems: "center"}}>
                  <label style={{display: "flex", alignItems: "center", gap: 7, cursor: "pointer", fontSize: 13}}>
                    <input type="checkbox" checked={(Number(vatPct) || 0) > 0} onChange={e => setVatPct(e.target.checked ? 7 : 0)}></input>
                    <span className="muted">คิดภาษีมูลค่าเพิ่ม (VAT 7%)</span>
                  </label>
                  <span className="amount">{(Number(vatPct) || 0) > 0 ? `฿${fmtM(vat)}` : "— ไม่คิด VAT"}</span>
                </div>
              )}
              <div style={{borderTop: "1px solid var(--line)", paddingTop: 6, marginTop: 4, display: "flex", justifyContent: "space-between", fontWeight: 600, fontSize: 15}}>
                <span>ยอดสุทธิ</span>
                <span className="amount">฿{fmtM(grand)}</span>
              </div>
            </div>

            <div className="field mt-lg">
              <label>หมายเหตุ</label>
              <div style={{display: "flex", flexWrap: "wrap", gap: 6, marginBottom: 8}}>
                {(window.DocNotePresets ? window.DocNotePresets.load() : []).map((p, i) => {
                  const on = notes.includes(p);
                  return (
                    <button key={i} type="button" onClick={() => setNotes(cur => on ? cur.split("\n").filter(l => l !== p).join("\n") : (cur ? cur + "\n" + p : p))}
                      style={{textAlign: "left", fontSize: 11.5, padding: "6px 10px", borderRadius: 8, cursor: "pointer", fontFamily: "var(--font)", maxWidth: "100%",
                        border: on ? "1.5px solid var(--accent)" : "1px solid var(--line)", background: on ? "var(--surface-2)" : "var(--surface)", color: on ? "var(--ink-1)" : "var(--ink-2)"}}>
                      {on ? "✓ " : "+ "}{p.replace(/^•\s*/, "")}
                    </button>
                  );
                })}
              </div>
              <textarea className="textarea" value={notes} onChange={e=>setNotes(e.target.value)} style={{minHeight: 80}} placeholder="เลือกจากการ์ดด้านบน หรือพิมพ์เอง"/>
              <div style={{fontSize: 10.5, color: "var(--ink-3)", marginTop: 4}}>ปรับรายการหมายเหตุได้ที่ ตั้งค่า → ตั้งค่าหมายเหตุเอกสาร</div>
            </div>
          </div>

          {/* RIGHT: Live preview */}
          <div style={{padding: 18, overflowY: "auto", background: "var(--surface-2)"}} className="newdoc-preview">
            <div className="h2 mb muted" style={{display: "flex", alignItems: "center", gap: 6}}>
              <I.doc size={14}/> ตัวอย่างเอกสาร (พิมพ์ได้)
            </div>
            <PrintablePaper
              cfg={cfg}
              docType={docType}
              docNo={docNo}
              date={date}
              dueDate={dueDate}
              validity={validity}
              expected={expected}
              method={method}
              party={party}
              lines={effLines.filter(l => l.name || l.qty > 0)}
              subtotal={subtotal}
              discount={Number(discount) || 0}
              vat={vat}
              vatPct={vatPct}
              grand={grand}
              notes={notes}
              withImages={canImages && withImages}
            />
          </div>
        </div>
        <div className="drawer-foot">
          <Btn kind="ghost" onClick={requestClose}>ยกเลิก</Btn>
          <Btn kind="ghost" onClick={save}>บันทึกร่าง</Btn>
          <Btn icon={I.print} onClick={saveAndPrint}>บันทึก + พิมพ์</Btn>
          <Btn kind="primary" icon={I.check} onClick={save}>บันทึก</Btn>
        </div>
      </div>
    </>
  );
}

// =============== Printable paper (used in preview + standalone print) ===============
function PrintablePaper({ cfg, docType, docNo, date, dueDate, validity, expected, method, party, lines, subtotal, discount, vat, vatPct, grand, notes, withImages }) {
  const showImg = !!withImages;
  const C = window.SSSData.Company;
  const afterDisc = subtotal - discount;
  const color = window.getDocColor(docType);
  const colorSoft = window.hexA(color, 0.07);
  const colorLine = window.hexA(color, 0.2);

  return (
    <div className="doc-paper print-target" style={{fontSize: 11.5, padding: 0, position: "relative", overflow: "hidden"}}>
      {/* Top color band */}
      <div style={{height: 6, background: color}}/>

      <div style={{padding: "26px 36px 32px"}}>
        {/* Header */}
        <div style={{display: "grid", gridTemplateColumns: "1fr auto", gap: 24, marginBottom: 24, alignItems: "flex-start"}}>
          <div style={{display: "flex", gap: 20, alignItems: "flex-start"}}>
            <div style={{background: color, borderRadius: 6, alignSelf: "stretch", minHeight: 56, maxHeight: 80, display: "flex", alignItems: "center", justifyContent: "center", padding: "8px 16px", flexShrink: 0}}><img src="assets/logo-ink.png" alt={C.name} style={{width: 132, maxHeight: "100%", objectFit: "contain", display: "block"}}/></div>
            <div style={{paddingTop: 2}}>
              <div style={{fontWeight: 700, fontSize: 13.5, lineHeight: 1.25, color: "#0c0a09"}}>{C.name}</div>
              <div style={{fontSize: 10.5, color: "#78716c", marginTop: 1}}>{C.nameEn}</div>
              <div style={{fontSize: 10.5, color: "#57534e", marginTop: 6, lineHeight: 1.5, maxWidth: 360}}>{C.address}</div>
              <div style={{display: "flex", gap: 14, fontSize: 10.5, color: "#57534e", marginTop: 3}}>
                <span>โทร {C.phone}</span>
                <span>{C.email}</span>
              </div>
              <div style={{fontSize: 10.5, color: "#57534e", marginTop: 1}}>เลขประจำตัวผู้เสียภาษี <b style={{color: "#0c0a09"}}>{C.taxId}</b> (สำนักงานใหญ่)</div>
            </div>
          </div>
          <div style={{textAlign: "right", minWidth: 200}}>
            <h1 style={{margin: 0, fontSize: 28, fontWeight: 700, color, letterSpacing: "-0.02em", lineHeight: 1, textTransform: "none"}}>{cfg.title}</h1>
            <div style={{fontSize: 9.5, color: "#a8a29e", letterSpacing: "0.12em", marginTop: 4, fontWeight: 500}}>{cfg.titleEn}</div>
            <div style={{marginTop: 14, display: "inline-block", textAlign: "left", background: colorSoft, padding: "10px 14px", borderRadius: 4, minWidth: 180}}>
              <div style={{display: "flex", justifyContent: "space-between", gap: 14, fontSize: 11}}><span style={{color: "#78716c"}}>เลขที่</span><b className="mono" style={{color: "#0c0a09"}}>{docNo}</b></div>
              <div style={{display: "flex", justifyContent: "space-between", gap: 14, fontSize: 11, marginTop: 3}}><span style={{color: "#78716c"}}>วันที่</span><b style={{color: "#0c0a09"}}>{date}</b></div>
              {cfg.showDue && <div style={{display: "flex", justifyContent: "space-between", gap: 14, fontSize: 11, marginTop: 3}}><span style={{color: "#78716c"}}>ครบกำหนด</span><b style={{color: "#0c0a09"}}>{dueDate}</b></div>}
              {cfg.showValidity && <div style={{display: "flex", justifyContent: "space-between", gap: 14, fontSize: 11, marginTop: 3}}><span style={{color: "#78716c"}}>ยืนราคา</span><b style={{color: "#0c0a09"}}>{validity}</b></div>}
              {cfg.showExpected && <div style={{display: "flex", justifyContent: "space-between", gap: 14, fontSize: 11, marginTop: 3}}><span style={{color: "#78716c"}}>นัดรับ</span><b style={{color: "#0c0a09"}}>{expected}</b></div>}
            </div>
          </div>
        </div>

        {/* Party info — 2 column boxes */}
        <div style={{display: "grid", gridTemplateColumns: "1fr 1fr", gap: 12, marginBottom: 16}}>
          <div style={{border: `1px solid ${colorLine}`, borderRadius: 5, overflow: "hidden"}}>
            <div style={{background: color, color: "white", padding: "5px 12px", fontSize: 10, fontWeight: 600, letterSpacing: "0.06em", textTransform: "uppercase"}}>{cfg.partyLabel}</div>
            <div style={{padding: "10px 12px", fontSize: 11.5}}>
              <div style={{fontWeight: 600, fontSize: 12.5, color: "#0c0a09"}}>{party?.name || "—"}</div>
              {party && (
                <div style={{color: "#57534e", marginTop: 3, lineHeight: 1.6}}>
                  <div>เลขผู้เสียภาษี <span className="mono" style={{color: "#0c0a09"}}>{party.taxId}</span></div>
                  <div>ผู้ติดต่อ: {party.contact}</div>
                  <div className="mono">{party.phone}</div>
                </div>
              )}
            </div>
          </div>
          <div style={{border: "1px solid #e7e5e4", borderRadius: 5, overflow: "hidden"}}>
            <div style={{background: "#f7f6f4", color: "#44403c", padding: "5px 12px", fontSize: 10, fontWeight: 600, letterSpacing: "0.06em", textTransform: "uppercase"}}>เงื่อนไข · อ้างอิง</div>
            <div style={{padding: "10px 12px", fontSize: 11.5, color: "#44403c", lineHeight: 1.7}}>
              {cfg.showDue && <div>เครดิต: <b>{party?.credit || 30} วัน</b> · ครบกำหนด {dueDate}</div>}
              {cfg.showMethod && <div>วิธี: <b>{method}</b></div>}
              {cfg.showValidity && <div>ยืนราคา: <b>{validity}</b></div>}
              <div>ผู้ออกเอกสาร: <b>{C.currentUser.name}</b></div>
              <div>โครงการ/อ้างอิง: <span className="mono">{docNo}</span></div>
            </div>
          </div>
        </div>

        {/* Line items table */}
        <table style={{borderCollapse: "separate", borderSpacing: 0, width: "100%"}}>
          <thead>
            <tr>
              <th style={{width: 30, background: color, color: "white", padding: "10px 6px", fontSize: 10.5, fontWeight: 600, textAlign: "center", borderTopLeftRadius: 4}}>#</th>
              {showImg && <th style={{width: 60, background: color, color: "white", padding: "10px 6px", fontSize: 10.5, fontWeight: 600, textAlign: "center"}}>รูป</th>}
              <th style={{background: color, color: "white", padding: "10px 12px", fontSize: 10.5, fontWeight: 600, textAlign: "left"}}>คำอธิบายรายการ</th>
              <th style={{width: 55, background: color, color: "white", padding: "10px 6px", fontSize: 10.5, fontWeight: 600, textAlign: "right"}}>จำนวน</th>
              <th style={{width: 55, background: color, color: "white", padding: "10px 6px", fontSize: 10.5, fontWeight: 600, textAlign: "left"}}>หน่วย</th>
              <th style={{width: 85, background: color, color: "white", padding: "10px 8px", fontSize: 10.5, fontWeight: 600, textAlign: "right"}}>ราคา/หน่วย</th>
              <th style={{width: 100, background: color, color: "white", padding: "10px 12px", fontSize: 10.5, fontWeight: 600, textAlign: "right", borderTopRightRadius: 4}}>มูลค่า</th>
            </tr>
          </thead>
          <tbody>
            {lines.length === 0 && (
              <tr><td colSpan={showImg ? 7 : 6} style={{padding: 26, textAlign: "center", color: "#a8a29e", fontStyle: "italic", borderBottom: "1px solid #e7e5e4"}}>(ยังไม่มีรายการ)</td></tr>
            )}
            {lines.map((l, i) => (
              <tr key={l.id} style={{background: i % 2 === 0 ? "white" : "#fafaf9"}}>
                <td style={{padding: "10px 6px", borderBottom: "1px solid #f1efeb", textAlign: "center", fontSize: 11, color: "#78716c"}}>{i + 1}</td>
                {showImg && (
                  <td style={{padding: "6px", borderBottom: "1px solid #f1efeb", textAlign: "center"}}>
                    {l.img
                      ? <img src={l.img} alt="" style={{width: 50, height: 50, objectFit: "cover", borderRadius: 4, border: "1px solid #e7e5e4", display: "inline-block"}}/>
                      : <div style={{width: 50, height: 50, borderRadius: 4, border: "1px dashed #d6d3d1", display: "inline-block"}}/>}
                  </td>
                )}
                <td style={{padding: "10px 12px", borderBottom: "1px solid #f1efeb"}}>
                  <div style={{fontWeight: 500, fontSize: 11.5, color: "#0c0a09"}}>{l.name || "—"}</div>
                  {l.sku && <div className="mono" style={{fontSize: 9.5, color: "#78716c", marginTop: 1}}>{l.sku}</div>}
                </td>
                <td style={{padding: "10px 6px", borderBottom: "1px solid #f1efeb", textAlign: "right", fontSize: 11}}>{l.qty}</td>
                <td style={{padding: "10px 6px", borderBottom: "1px solid #f1efeb", fontSize: 11, color: "#57534e"}}>{l.unit}</td>
                <td style={{padding: "10px 8px", borderBottom: "1px solid #f1efeb", textAlign: "right", fontSize: 11}}>{fmtM(Number(l.price) || 0)}</td>
                <td style={{padding: "10px 12px", borderBottom: "1px solid #f1efeb", textAlign: "right", fontSize: 11, fontWeight: 600, color: "#0c0a09"}}>{fmtM((Number(l.qty)||0) * (Number(l.price)||0))}</td>
              </tr>
            ))}
          </tbody>
        </table>

        {/* Totals + notes */}
        <div style={{display: "grid", gridTemplateColumns: "1.1fr 1fr", gap: 24, marginTop: 18}}>
          <div style={{fontSize: 10.5, color: "#57534e", lineHeight: 1.6, whiteSpace: "pre-line"}}>
            <div style={{textTransform: "uppercase", fontSize: 9.5, fontWeight: 700, color: "#44403c", letterSpacing: "0.08em", marginBottom: 6, paddingBottom: 4, borderBottom: `2px solid ${color}`, display: "inline-block"}}>หมายเหตุ</div>
            <div style={{marginTop: 4}}>{notes}</div>
            {cfg.showMethod && cfg.party === "customer" && (
              <div style={{marginTop: 12, padding: "8px 12px", background: "#fefdf9", border: "1px solid #f1efeb", borderRadius: 4, fontSize: 10.5}}>
                <b style={{color: "#0c0a09"}}>ช่องทางชำระเงิน:</b><br/>{C.bank}
              </div>
            )}
          </div>
          <div>
            <div style={{padding: "10px 14px", background: "#f7f6f4", borderRadius: "5px 5px 0 0", border: "1px solid #e7e5e4"}}>
              <div style={{display: "flex", justifyContent: "space-between", padding: "3px 0", fontSize: 11.5, color: "#57534e"}}><span>รวมเป็นเงิน</span><span style={{color: "#0c0a09"}}>{fmtM(subtotal)}</span></div>
              {discount > 0 && <div style={{display: "flex", justifyContent: "space-between", padding: "3px 0", fontSize: 11.5, color: "#57534e"}}><span>ส่วนลด</span><span style={{color: "#0c0a09"}}>−{fmtM(discount)}</span></div>}
              {discount > 0 && <div style={{display: "flex", justifyContent: "space-between", padding: "3px 0", fontSize: 11.5, color: "#57534e"}}><span>หลังหักส่วนลด</span><span style={{color: "#0c0a09"}}>{fmtM(afterDisc)}</span></div>}
              {cfg.showVAT && <div style={{display: "flex", justifyContent: "space-between", padding: "3px 0", fontSize: 11.5, color: "#57534e"}}><span>ภาษีมูลค่าเพิ่ม {vatPct}%</span><span style={{color: "#0c0a09"}}>{fmtM(vat)}</span></div>}
            </div>
            <div style={{display: "flex", justifyContent: "space-between", alignItems: "center", padding: "14px 14px", background: color, color: "white", borderRadius: "0 0 5px 5px"}}>
              <span style={{fontSize: 12.5, fontWeight: 500}}>จำนวนเงินรวมทั้งสิ้น</span>
              <span style={{fontSize: 17, fontWeight: 700, fontVariantNumeric: "tabular-nums"}}>฿ {fmtM(grand)}</span>
            </div>
            <div style={{padding: "6px 14px", fontSize: 10.5, color: "#57534e", fontStyle: "italic", textAlign: "right"}}>
              ({bahtText(grand)})
            </div>
            {cfg.showStamp && (
              <div style={{marginTop: 8, textAlign: "center"}}>
                <span style={{display: "inline-block", padding: "6px 22px", border: `2.5px solid ${color}`, color, fontWeight: 700, fontSize: 12, letterSpacing: "0.14em", borderRadius: 4, transform: "rotate(-3deg)"}}>PAID · ชำระแล้ว</span>
              </div>
            )}
          </div>
        </div>

        {/* Signatures */}
        <div style={{display: "grid", gridTemplateColumns: `repeat(${cfg.showSign.length}, 1fr)`, gap: 30, marginTop: 44, fontSize: 10.5}}>
          {cfg.showSign.map((s, i) => (
            <div key={i} style={{textAlign: "center"}}>
              <div style={{borderTop: "1px dashed #57534e", paddingTop: 6, marginTop: 38}}>
                <div style={{fontWeight: 600, color: "#0c0a09"}}>{s}</div>
                <div style={{color: "#78716c", fontSize: 10}}>วันที่ ____________</div>
              </div>
            </div>
          ))}
        </div>

        {/* Footer */}
        <div style={{marginTop: 28, paddingTop: 10, borderTop: `2px solid ${color}`, fontSize: 9.5, color: "#78716c", display: "flex", justifyContent: "space-between", alignItems: "center"}}>
          <span><b style={{color: "#44403c"}}>{C.name}</b> · {C.website}</span>
          <span>{docNo} · ออกโดยระบบ SSS</span>
        </div>
      </div>
    </div>
  );
}

// =============== Global helper ===============
function NewDocHost() {
  const [docType, setDocType] = useStateN(null);
  const [prefill, setPrefill] = useStateN(null);
  useEffectN(() => {
    window.openNewDoc = (type, pf) => { setPrefill(pf || null); setDocType(type); };
  }, []);
  if (!docType) return null;
  return <NewDocDrawer key={(prefill && prefill.docNo) || docType} docType={docType} prefill={prefill} onClose={() => { setDocType(null); setPrefill(null); }}/>;
}

window.NewDocHost = NewDocHost;
window.DOC_TYPES = DOC_TYPES;
window.NewDocPrintablePaper = PrintablePaper;
