/* Viamar Desktop — Compliance step, estimate transparency, document helpers
   Built from real Viamar policy documents:
   · EU ICS2 filing (mandatory complete consignee contact, eff. June 2024)
   · Stolen-vehicle advisory (paid-in-full + ownership / ID / bill of sale)
   · Household groupage booking terms (no lithium / e-bikes / hazmat, declared value)
   · Demurrage & detention + customs inspection fee transparency */

// shared small field
function Field({ label, value, onChange, placeholder, required, half }) {
  const filled = value && value.trim().length > 0;
  return (
    <div style={{ flex: half ? 1 : undefined, width: half ? undefined : '100%' }}>
      <div style={{ fontFamily: FM, fontSize: 9.5, letterSpacing: 0.8, color: T.faint, textTransform: 'uppercase', marginBottom: 6 }}>
        {label}{required && <span style={{ color: T.red }}> *</span>}
      </div>
      <input value={value} onChange={e => onChange(e.target.value)} placeholder={placeholder} style={{
        width: '100%', border: '1.5px solid ' + (required && !filled ? 'rgba(221,28,36,0.35)' : T.line), borderRadius: 11,
        padding: '11px 13px', fontFamily: FB, fontSize: 14, color: T.ink, background: '#fff', outline: 'none',
      }} />
    </div>
  );
}

function CheckCard({ on, onToggle, title, sub, tone = 'navy' }) {
  const c = tone === 'red' ? T.red : T.green;
  return (
    <div onClick={onToggle} style={{ display: 'flex', alignItems: 'flex-start', gap: 13, background: '#fff', borderRadius: 14, padding: '15px 16px', cursor: 'pointer', border: `2px solid ${on ? c : T.line2}`, transition: 'border .15s' }}>
      <div style={{ width: 24, height: 24, borderRadius: 7, flexShrink: 0, marginTop: 1, background: on ? c : '#fff', border: on ? 'none' : '2px solid ' + T.line, display: 'flex', alignItems: 'center', justifyContent: 'center' }}>
        {on && <Icon name="check" size={15} color="#fff" stroke={3} />}
      </div>
      <div>
        <div style={{ fontFamily: FB, fontWeight: 700, fontSize: 14, color: T.ink }}>{title}</div>
        {sub && <div style={{ fontFamily: FB, fontSize: 12, color: T.muted, lineHeight: 1.45, marginTop: 2 }}>{sub}</div>}
      </div>
    </div>
  );
}

function DocUploadRow({ name, sub, attached, onAttach, uploading, error }) {
  const inputRef = React.useRef(null);
  const attachedLabel = attached && attached.queued ? 'Queued' : 'Attached';
  return (
    <div style={{ display: 'flex', alignItems: 'center', gap: 13, padding: '13px 16px', borderTop: '1px solid ' + T.line2 }}>
      <input ref={inputRef} type="file" accept="application/pdf,image/jpeg,image/png,image/webp,image/heic,image/heif" hidden
        onChange={e => {
          const file = e.target.files && e.target.files[0];
          e.target.value = '';
          if (file) onAttach(file);
        }} />
      <div style={{ width: 38, height: 38, borderRadius: 10, background: attached ? 'rgba(46,139,111,0.12)' : T.paper, display: 'flex', alignItems: 'center', justifyContent: 'center', flexShrink: 0 }}>
        <Icon name={attached ? 'checkC' : 'doc'} size={19} color={attached ? T.green : T.navy} stroke={1.9} />
      </div>
      <div style={{ flex: 1 }}>
        <div style={{ fontFamily: FB, fontWeight: 600, fontSize: 13.5, color: T.ink }}>{name}</div>
        {sub && <div style={{ fontFamily: FB, fontSize: 11.5, color: T.muted }}>{sub}</div>}
        {error && <div style={{ fontFamily: FB, fontSize: 10.5, color: T.red, marginTop: 3 }}>{error}</div>}
      </div>
      {uploading
        ? <span style={{ fontFamily: FM, fontSize: 10.5, color: T.navy3, letterSpacing: 0.3 }}>Uploading...</span>
        : attached
          ? <span style={{ fontFamily: FM, fontSize: 10.5, color: T.green, letterSpacing: 0.3 }}>{attachedLabel}</span>
          : <Btn variant="ghost" size="sm" icon="plus" onClick={() => inputRef.current && inputRef.current.click()}>Upload</Btn>}
    </div>
  );
}

// ── The compliance step ────────────────────────────────────
function ComplianceStep({ cargo, service, dest, comp, setComp, quoteRef }) {
  const isVehicle = cargo === 'car' || cargo === 'bike';
  const isEU = service === 'intl' && dest && dest.region === 'Europe';
  const isHousehold = cargo === 'box' || cargo === 'ship';
  const [uploadingDocs, setUploadingDocs] = React.useState({});
  const [uploadErrors, setUploadErrors] = React.useState({});
  const set = (patch) => setComp(c => ({ ...c, ...patch }));
  const setDoc = (k, file) => {
    setUploadErrors(e => ({ ...e, [k]: null }));
    setUploadingDocs(u => ({ ...u, [k]: true }));
    if (window.ViamarAnalytics) ViamarAnalytics.track('document_uploaded', {
      document_type: k,
      cargo_type: cargo,
      service: service,
      destination_country: dest && dest.country,
      file_type: file && file.type,
    });
    const finish = (result) => {
      setComp(c => ({ ...c, docs: { ...c.docs, [k]: result || true } }));
      setUploadingDocs(u => ({ ...u, [k]: false }));
    };
    if (window.ViamarAPI && file) {
      ViamarAPI.uploadDocument({
        quote_ref: quoteRef,
        document_type: k,
        file: file,
        cargo_type: cargo,
        service: service,
        destination_country: dest && dest.country,
        source: 'desktop-compliance',
      }).then(finish).catch(function (err) {
        setUploadingDocs(u => ({ ...u, [k]: false }));
        setUploadErrors(e => ({ ...e, [k]: (err && err.message) || 'Upload failed' }));
      });
    } else {
      finish({ queued: true, file_name: file && file.name });
    }
  };
  const setCon = (k, v) => setComp(c => ({ ...c, consignee: { ...c.consignee, [k]: v } }));

  return (
    <div style={{ display: 'flex', flexDirection: 'column', gap: 22 }}>
      {/* Vehicle export compliance */}
      {isVehicle && (
        <div>
          <div style={{ display: 'flex', alignItems: 'flex-start', gap: 12, background: 'rgba(221,28,36,0.06)', border: '1px solid rgba(221,28,36,0.2)', borderRadius: 14, padding: '14px 16px', marginBottom: 14 }}>
            <Icon name="shield" size={20} color={T.red} stroke={2} />
            <div>
              <div style={{ fontFamily: FB, fontWeight: 700, fontSize: 13.5, color: T.ink }}>Vehicle export compliance required</div>
              <div style={{ fontFamily: FB, fontSize: 12, color: T.body, lineHeight: 1.5, marginTop: 3 }}>Police are checking nearly all containers for ownership before terminals. Vehicles without these documents cannot be accepted for shipping.</div>
            </div>
          </div>
          <CheckCard tone="red" on={comp.paidInFull} onToggle={() => set({ paidInFull: !comp.paidInFull })}
            title="The vehicle is paid in full"
            sub="No active lease, finance or loan. A lien-free vehicle is required to export from Canada." />

          {/* vehicle identity */}
          <div style={{ background: '#fff', borderRadius: 14, border: '1px solid ' + T.line2, padding: 16, marginTop: 12 }}>
            <Kicker color={T.navy3} style={{ marginBottom: 12 }}>Vehicle identity</Kicker>
            <div style={{ display: 'flex', flexDirection: 'column', gap: 12 }}>
              <Field label="VIN" value={comp.vin || ''} onChange={v => set({ vin: v.toUpperCase() })} placeholder="17-character vehicle identification number" />
              <div style={{ display: 'flex', gap: 12 }}>
                <Field half label="Year & make" value={comp.vmake || ''} onChange={v => set({ vmake: v })} placeholder="2023 BMW" />
                <Field half label="Model" value={comp.vmodel || ''} onChange={v => set({ vmodel: v })} placeholder="M4 Competition" />
              </div>
            </div>
          </div>

          <div style={{ background: '#fff', borderRadius: 14, border: '1px solid ' + T.line2, overflow: 'hidden', marginTop: 12 }}>
            <div style={{ padding: '12px 16px', fontFamily: FM, fontSize: 10, letterSpacing: 0.8, color: T.faint, textTransform: 'uppercase' }}>Required documents</div>
            <DocUploadRow name="Canadian photo ID" sub="Driver's licence or passport" attached={comp.docs.id} uploading={uploadingDocs.id} error={uploadErrors.id} onAttach={file => setDoc('id', file)} />
            <DocUploadRow name="Vehicle ownership / registration" sub="Current Ontario registration" attached={comp.docs.ownership} uploading={uploadingDocs.ownership} error={uploadErrors.ownership} onAttach={file => setDoc('ownership', file)} />
            <DocUploadRow name="Bill of sale or release letter" sub="Release letter from financial institution if applicable" attached={comp.docs.bill} uploading={uploadingDocs.bill} error={uploadErrors.bill} onAttach={file => setDoc('bill', file)} />
          </div>
          <div style={{ fontFamily: FB, fontSize: 11.5, color: T.muted, lineHeight: 1.5, marginTop: 10, paddingLeft: 2 }}>
            In some cases we may also request the Used Vehicle Package from Service Ontario or a complete CARFAX showing no liens.
          </div>
        </div>
      )}

      {/* ICS2 consignee details — EU */}
      {isEU && (
        <div>
          <div style={{ display: 'flex', alignItems: 'center', gap: 9, marginBottom: 12 }}>
            <Kicker color={T.navy3}>Destination consignee · {dest.country}</Kicker>
            <span style={{ fontFamily: FM, fontSize: 9.5, fontWeight: 700, color: T.red, background: 'rgba(221,28,36,0.08)', padding: '4px 9px', borderRadius: 999, letterSpacing: 0.3, textTransform: 'uppercase' }}>Mandatory · ICS2 (Jun 2024)</span>
          </div>
          <div style={{ fontFamily: FB, fontSize: 12.5, color: T.body, lineHeight: 1.5, marginBottom: 14 }}>
            EU customs require complete contact details for whoever receives the shipment. Missing details can trigger fines, extra inspections and storage charges.
          </div>
          <div style={{ display: 'flex', flexDirection: 'column', gap: 12 }}>
            <Field label="Full name" value={comp.consignee.name} onChange={v => setCon('name', v)} placeholder="Recipient full name" required />
            <Field label="Complete address (incl. postal code)" value={comp.consignee.addr} onChange={v => setCon('addr', v)} placeholder="Street, city, postal code" required />
            <div style={{ display: 'flex', gap: 12 }}>
              <Field half label="Phone" value={comp.consignee.phone} onChange={v => setCon('phone', v)} placeholder="+39 …" required />
              <Field half label="Email" value={comp.consignee.email} onChange={v => setCon('email', v)} placeholder="name@email.com" required />
            </div>
          </div>
        </div>
      )}

      {/* Household groupage rules */}
      {isHousehold && (
        <div>
          <Kicker color={T.navy3} style={{ marginBottom: 12 }}>Household goods</Kicker>
          <CheckCard tone="red" on={comp.prohibitedAck} onToggle={() => set({ prohibitedAck: !comp.prohibitedAck })}
            title="No prohibited items in my shipment"
            sub="No lithium batteries, e-bikes or any hazardous goods. Goods delivered packed & wrapped to our warehouse — Viamar palletizes." />
          <div style={{ marginTop: 14, background: '#fff', borderRadius: 14, border: '1px solid ' + T.line2, padding: 16 }}>
            <div style={{ display: 'flex', alignItems: 'center', justifyContent: 'space-between', gap: 14 }}>
              <div style={{ flex: 1 }}>
                <div style={{ fontFamily: FB, fontWeight: 700, fontSize: 13.5, color: T.ink }}>Declared value for cargo insurance</div>
                <div style={{ fontFamily: FB, fontSize: 11.5, color: T.muted, marginTop: 2 }}>Optional — quoted rates exclude marine cargo insurance.</div>
              </div>
              <div style={{ display: 'flex', alignItems: 'center', gap: 6, border: '1.5px solid ' + T.line, borderRadius: 11, padding: '9px 13px' }}>
                <span style={{ fontFamily: FM, fontSize: 14, color: T.muted }}>$</span>
                <input value={comp.declared} onChange={e => set({ declared: e.target.value.replace(/[^0-9]/g, '') })} placeholder="0" style={{ width: 90, border: 'none', outline: 'none', fontFamily: FB, fontWeight: 700, fontSize: 15, color: T.ink, textAlign: 'right' }} />
                <span style={{ fontFamily: FM, fontSize: 11, color: T.faint }}>CAD</span>
              </div>
            </div>
            {comp.declared && Number(comp.declared) > 0 && (
              <div style={{ marginTop: 12, paddingTop: 12, borderTop: '1px solid ' + T.line2, display: 'flex', justifyContent: 'space-between', fontFamily: FB, fontSize: 13 }}>
                <span style={{ color: T.body }}>Estimated insurance premium (≈3%)</span>
                <span style={{ fontFamily: FM, fontWeight: 700, color: T.ink }}>${Math.round(Number(comp.declared) * 0.03).toLocaleString()}</span>
              </div>
            )}
          </div>
        </div>
      )}
    </div>
  );
}

// Validation for the compliance step
function complianceValid(cargo, service, dest, comp) {
  const isVehicle = cargo === 'car' || cargo === 'bike';
  const isEU = service === 'intl' && dest && dest.region === 'Europe';
  const isHousehold = cargo === 'box' || cargo === 'ship';
  if (isVehicle && !(comp.paidInFull && comp.docs.id && comp.docs.ownership && comp.docs.bill)) return false;
  if (isEU) { const c = comp.consignee; if (!(c.name && c.addr && c.phone && c.email)) return false; }
  if (isHousehold && !comp.prohibitedAck) return false;
  return true;
}

// ── Estimate transparency block (rendered under shared StepEstimate) ──
function EstimateExtras({ cargo, service }) {
  const isHousehold = cargo === 'box' || cargo === 'ship';
  const storage = isHousehold ? '30 days free storage at Courtice' : '2 weeks free storage at Courtice';
  const included = service === 'domestic'
    ? ['Door-to-door pickup & handling', 'Documentation', storage]
    : ['Destination terminal charges', 'Customs clearance at destination', 'Curbside delivery to residence', storage];
  const isLCL = service !== 'domestic' && isHousehold;
  return (
    <div style={{ marginTop: 18 }}>
      <div style={{ background: '#fff', borderRadius: 16, border: '1px solid ' + T.line2, padding: 18, marginBottom: 12 }}>
        <Kicker color={T.green} style={{ marginBottom: 12 }}>What's included</Kicker>
        <div style={{ display: 'grid', gridTemplateColumns: '1fr 1fr', gap: '9px 18px' }}>
          {included.map((t, i) => (
            <div key={i} style={{ display: 'flex', alignItems: 'center', gap: 9 }}>
              <Icon name="checkC" size={17} color={T.green} stroke={2} />
              <span style={{ fontFamily: FB, fontSize: 13, color: T.body }}>{t}</span>
            </div>
          ))}
        </div>
        {isHousehold && (
          <div style={{ fontFamily: FB, fontSize: 11.5, color: T.muted, lineHeight: 1.5, marginTop: 12, paddingTop: 12, borderTop: '1px solid ' + T.line2 }}>
            Deliver your goods <span style={{ color: T.ink, fontWeight: 700 }}>packed &amp; wrapped</span> to our Courtice warehouse — we palletize and load in-house. Rate is based on the volume quoted; any additional volume is charged at <span style={{ color: T.ink, fontWeight: 700 }}>$400 / m³</span>.
          </div>
        )}
      </div>

      <div style={{ background: T.navy, borderRadius: 16, padding: 18 }}>
        <div style={{ display: 'flex', alignItems: 'center', gap: 9, marginBottom: 10 }}>
          <Icon name="shield" size={17} color={T.gold} stroke={2} />
          <span style={{ fontFamily: FM, fontSize: 10, fontWeight: 700, color: 'rgba(255,255,255,0.8)', letterSpacing: 0.8, textTransform: 'uppercase' }}>Good to know · full transparency</span>
        </div>
        <div style={{ fontFamily: FB, fontSize: 12.5, color: 'rgba(255,255,255,0.72)', lineHeight: 1.55 }}>
          Customs may inspect ~10–15% of shipments, and rail-terminal congestion can occasionally cause demurrage or detention. If any third-party charges arise, we pass them on <span style={{ color: '#fff', fontWeight: 700 }}>at cost — never marked up</span> — and keep you informed every step.{isLCL && <span> On a shared (LCL) container, those charges are <span style={{ color: '#fff', fontWeight: 700 }}>split across all customers</span> on the load; full containers (FCL) cover their own.</span>}
        </div>
      </div>
    </div>
  );
}

// ── Documents & compliance checklist for a tracked shipment ──
function complianceDocsFor(s) {
  const eu = /Bremerhaven|Genoa|Lisbon|Germany|Italy|Portugal|DE|IT|PT/.test(s.to + ' ' + s.toPort);
  const delivered = s.kind === 'delivered';
  const ok = (cond) => cond ? 'Verified' : 'Pending';
  if (s.cargoType === 'car' || s.cargoType === 'bike') {
    return [
      ['Proof of ownership / registration', 'doc', 'Verified'],
      ['Bill of sale · lien-free', 'shield', 'Verified'],
      ['Canadian photo ID', 'user', 'Verified'],
      eu ? ['ICS2 consignee details', 'pin', 'Verified'] : ['Export declaration', 'doc', 'Verified'],
      ['Bill of lading', 'doc', s.ref !== '—' ? s.ref : 'Pending'],
    ];
  }
  return [
    ['Packing list', 'doc', 'Verified'],
    ['Prohibited-items declaration', 'shield', 'Verified'],
    eu ? ['ICS2 consignee details', 'pin', ok(!delivered ? true : true)] : ['Commercial invoice', 'doc', 'Attached'],
    ['Cargo insurance', 'shield', delivered ? 'Closed' : 'Optional'],
    ['Bill of lading', 'doc', s.ref !== '—' ? s.ref : 'Pending'],
  ];
}

// ── Quote price (mirrors the shared estimate's method table) ──
function quotePrice(cargo, service, method) {
  let methods;
  if (service === 'domestic') methods = [
    { id: 'shared', name: 'Shared container', price: 580, days: '5–7 days' },
    { id: 'truck', name: 'Dedicated truck', price: 1240, days: '3–4 days' },
  ];
  else if (cargo === 'car' || cargo === 'bike') methods = [
    { id: 'shared', name: 'Shared container', price: 1850, days: '14–18 days' },
    { id: 'fcl', name: 'Full container (40ft)', price: 4200, days: '14–18 days' },
    { id: 'roro', name: 'RORO', price: 1400, days: '18–24 days' },
  ];
  else methods = [
    { id: 'lcl', name: 'LCL consolidated', price: 1320, days: '15–19 days' },
    { id: 'fcl20', name: 'Full 20ft container', price: 3100, days: '15–19 days' },
  ];
  return methods.find(m => m.id === method) || methods[0];
}

// ── Step 6 — Review, sign & pay ──
function contactChannelValid(pay) {
  const email = (pay.email || '').trim();
  const phoneDigits = (pay.phone || '').replace(/\D/g, '');
  return /^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(email) || phoneDigits.length >= 7;
}

function StripePaymentBox({ quoteRef, amount, pay, cargo, service, dest, paymentState, setPaymentState }) {
  const mountId = React.useMemo(() => 'stripe-payment-' + quoteRef, [quoteRef]);
  const readyForStripe = pay.method === 'card' && contactChannelValid(pay) && pay.sign && pay.sign.trim().length > 1;

  React.useEffect(() => {
    let cancelled = false;
    if (!readyForStripe) return undefined;
    if (paymentState && (paymentState.status === 'ready' || paymentState.status === 'loading')) return undefined;

    setPaymentState({ status: 'loading', message: 'Preparing secure card authorization...' });
    if (!window.ViamarAPI) {
      setPaymentState({ status: 'manual', provider: 'manual', message: 'Backend is not configured. Viamar will contact you for payment.' });
      return undefined;
    }

    ViamarAPI.createPaymentIntent({
      quote_ref: quoteRef,
      amount: amount,
      currency: 'cad',
      method: 'card',
      customer: { name: pay.sign, email: pay.email, phone: pay.phone },
      source: 'desktop-payment-element',
    }).then(result => {
      if (cancelled) return;
      if (!result || !result.client_secret || !result.publishable_key || !window.Stripe) {
        setPaymentState({ status: 'manual', provider: result && result.provider, payment: result, message: result && result.instructions ? result.instructions : 'Stripe is not available. Viamar will contact you for payment.' });
        return;
      }
      const stripe = window.Stripe(result.publishable_key);
      const elements = stripe.elements({
        clientSecret: result.client_secret,
        appearance: {
          theme: 'stripe',
          variables: { colorPrimary: T.red, colorText: T.ink, borderRadius: '12px', fontFamily: 'Archivo, sans-serif' },
        },
      });
      const paymentElement = elements.create('payment');
      setTimeout(() => {
        const mount = document.getElementById(mountId);
        if (!cancelled && mount) {
          paymentElement.mount(mount);
          setPaymentState({ status: 'ready', provider: 'stripe', payment: result, stripe, elements, message: 'Secure card authorization ready.' });
        }
      }, 0);
    }).catch(err => {
      if (!cancelled) setPaymentState({ status: 'error', message: (err && err.message) || 'Payment setup failed. Viamar will contact you for payment.' });
    });

    return () => { cancelled = true; };
  }, [readyForStripe, quoteRef, amount, pay.email, pay.phone, pay.sign, pay.method]);

  if (pay.method !== 'card') return null;

  return (
    <div style={{ background: '#fff', border: '1px solid ' + T.line2, borderRadius: 14, padding: 16, marginTop: 12 }}>
      <div style={{ display: 'flex', alignItems: 'center', gap: 9, marginBottom: 10 }}>
        <Icon name="shield" size={17} color={T.navy3} stroke={2} />
        <span style={{ fontFamily: FM, fontSize: 10, letterSpacing: 0.8, color: T.faint, textTransform: 'uppercase' }}>Secure card authorization</span>
      </div>
      {!readyForStripe && (
        <div style={{ fontFamily: FB, fontSize: 12.5, color: T.body, lineHeight: 1.5 }}>Add contact details and signature above to prepare the secure card form.</div>
      )}
      {readyForStripe && (
        <>
          <div id={mountId} style={{ minHeight: paymentState && paymentState.status === 'ready' ? 142 : 36 }} />
          <div style={{ fontFamily: FB, fontSize: 11.5, color: paymentState && paymentState.status === 'error' ? T.red : T.muted, lineHeight: 1.45, marginTop: 10 }}>
            {(paymentState && paymentState.message) || 'Preparing secure card authorization...'}
          </div>
        </>
      )}
    </div>
  );
}

function ReviewSignPay({ cargo, service, dest, method, pay, setPay, quoteRef, paymentState, setPaymentState }) {
  const m = quotePrice(cargo, service, method);
  const cargoLabel = (CARGO_TYPES.find(c => c.id === cargo) || {}).label || 'Shipment';
  const today = new Date().toLocaleDateString('en-CA', { year: 'numeric', month: 'short', day: 'numeric' });
  const set = (patch) => setPay(p => ({ ...p, ...patch }));
  const payOptions = [['card', 'Card'], ['etransfer', 'Interac e-Transfer'], ['wire', 'Wire / EFT']];
  return (
    <div style={{ display: 'flex', flexDirection: 'column', gap: 20 }}>
      {/* booking summary */}
      <div style={{ background: T.navy, borderRadius: 18, padding: 22 }}>
        <div style={{ display: 'flex', alignItems: 'center', justifyContent: 'space-between', marginBottom: 16 }}>
          <Kicker color={T.red}>Booking summary</Kicker>
          <span style={{ fontFamily: FM, fontSize: 9.5, fontWeight: 700, color: T.gold, background: 'rgba(200,162,75,0.14)', padding: '4px 10px', borderRadius: 999, letterSpacing: 0.5, textTransform: 'uppercase' }}>Prepaid</span>
        </div>
        <div style={{ display: 'grid', gridTemplateColumns: '1fr 1fr', gap: '14px 16px', marginBottom: 18 }}>
          {[['Route', dest ? `Toronto → ${dest.city}, ${dest.country}` : 'Toronto → —'], ['Cargo', cargoLabel], ['Method', m.name], ['Transit', m.days]].map(([l, v], i) => (
            <div key={i}>
              <div style={{ fontFamily: FM, fontSize: 8.5, letterSpacing: 0.8, color: 'rgba(255,255,255,0.45)', textTransform: 'uppercase' }}>{l}</div>
              <div style={{ fontFamily: FB, fontWeight: 700, fontSize: 13.5, color: '#fff', marginTop: 3 }}>{v}</div>
            </div>
          ))}
        </div>
        <div style={{ display: 'flex', alignItems: 'baseline', gap: 8, paddingTop: 16, borderTop: '1px solid rgba(255,255,255,0.1)' }}>
          <span style={{ fontFamily: FB, fontSize: 13, color: 'rgba(255,255,255,0.6)', flex: 1 }}>Estimated total · locks once your agent confirms</span>
          <span style={{ fontFamily: FD, fontWeight: 900, fontSize: 30, color: '#fff', fontStretch: '120%' }}>${m.price.toLocaleString()}</span>
          <span style={{ fontFamily: FM, fontSize: 11, color: 'rgba(255,255,255,0.5)' }}>CAD</span>
        </div>
      </div>

      {/* customer contact */}
      <div>
        <Kicker color={T.navy3} style={{ marginBottom: 10 }}>Customer contact</Kicker>
        <div style={{ background: '#fff', border: '1px solid ' + T.line2, borderRadius: 14, padding: 16 }}>
          <div style={{ fontFamily: FB, fontSize: 12.5, color: T.body, lineHeight: 1.5, marginBottom: 13 }}>
            This is where Viamar sends the confirmed price, document requests, and payment instructions after agent review.
          </div>
          <div style={{ display: 'flex', gap: 12 }}>
            <Field half label="Email" value={pay.email || ''} onChange={v => set({ email: v })} placeholder="name@email.com" required={!pay.phone} />
            <Field half label="Phone" value={pay.phone || ''} onChange={v => set({ phone: v })} placeholder="+1 416 555 0100" required={!pay.email} />
          </div>
          {!contactChannelValid(pay) && (
            <div style={{ fontFamily: FB, fontSize: 11.5, color: T.red, marginTop: 10 }}>Add a valid email or phone number to submit the booking.</div>
          )}
        </div>
      </div>

      {/* terms */}
      <CheckCard tone="green" on={pay.terms} onToggle={() => set({ terms: !pay.terms })}
        title="I accept Viamar's standard trading terms"
        sub="This booking trades under C.I.F.F.A. (Canadian International Freight Forwarders Association) standard terms & conditions. Quoted rates exclude marine cargo insurance." />
      <div style={{ marginTop: -10, marginBottom: 4, fontFamily: FM, fontSize: 11, color: T.muted }}>
        Review the app acknowledgement: <a href={window.VIAMAR_TERMS_URL || 'terms.html'} target="_blank" rel="noreferrer" style={{ color: T.red, fontWeight: 800 }}>terms reference</a>
        {' · '}
        <a href={window.VIAMAR_PRIVACY_URL || 'privacy.html'} target="_blank" rel="noreferrer" style={{ color: T.red, fontWeight: 800 }}>data handling</a>
      </div>

      {/* signature */}
      <div>
        <Kicker color={T.navy3} style={{ marginBottom: 10 }}>Authorised signature</Kicker>
        <div style={{ display: 'flex', gap: 12, alignItems: 'flex-end' }}>
          <div style={{ flex: 1 }}>
            <Field label="Type your full legal name to sign" value={pay.sign} onChange={v => set({ sign: v })} placeholder="Full name" required />
          </div>
          <div style={{ width: 150 }}>
            <div style={{ fontFamily: FM, fontSize: 9.5, letterSpacing: 0.8, color: T.faint, textTransform: 'uppercase', marginBottom: 6 }}>Date</div>
            <div style={{ border: '1.5px solid ' + T.line, borderRadius: 11, padding: '11px 13px', fontFamily: FB, fontSize: 14, color: T.body, background: T.paper }}>{today}</div>
          </div>
        </div>
        {pay.sign && (
          <div style={{ marginTop: 10, background: '#fff', border: '1px dashed ' + T.line, borderRadius: 12, padding: '12px 16px', display: 'flex', alignItems: 'center', gap: 10 }}>
            <span style={{ fontFamily: 'Snell Roundhand, Apple Chancery, cursive', fontSize: 26, color: T.ink, fontStyle: 'italic' }}>{pay.sign}</span>
            <span style={{ marginLeft: 'auto', fontFamily: FM, fontSize: 10, color: T.faint, letterSpacing: 0.3 }}>e-signed · {today}</span>
          </div>
        )}
      </div>

      {/* payment */}
      <div>
        <Kicker color={T.navy3} style={{ marginBottom: 10 }}>Prepayment method</Kicker>
        <div style={{ display: 'flex', gap: 9, marginBottom: 12 }}>
          {payOptions.map(([id, lbl]) => {
            const on = pay.method === id;
            return (
              <div key={id} onClick={() => set({ method: id })} style={{ flex: 1, textAlign: 'center', padding: '13px 10px', borderRadius: 13, cursor: 'pointer', border: `2px solid ${on ? T.red : T.line2}`, background: '#fff', fontFamily: FB, fontWeight: 700, fontSize: 13, color: on ? T.ink : T.muted }}>{lbl}</div>
            );
          })}
        </div>
        <div style={{ display: 'flex', gap: 11, background: 'rgba(46,139,111,0.07)', border: '1px solid rgba(46,139,111,0.2)', borderRadius: 13, padding: '13px 15px' }}>
          <Icon name="shield" size={18} color={T.green} stroke={2} />
          <div style={{ fontFamily: FB, fontSize: 12, color: T.body, lineHeight: 1.5 }}>
            Shipments are <span style={{ color: T.ink, fontWeight: 700 }}>prepaid in full</span>. You're authorised now and charged only once your agent confirms the final price (usually within 1 business hour). No documents are released until payment clears.
          </div>
        </div>
        <StripePaymentBox quoteRef={quoteRef} amount={m.price} pay={pay} cargo={cargo} service={service} dest={dest} paymentState={paymentState} setPaymentState={setPaymentState} />
      </div>
    </div>
  );
}

function reviewValid(pay) {
  return !!(pay.terms && pay.sign && pay.sign.trim().length > 1 && contactChannelValid(pay));
}

// ── Payment status bar for tracked shipments (PREPAID model) ──
function PaymentBar({ s }) {
  const pending = s.kind === 'review';
  const c = pending ? T.amber : T.green;
  const bg = pending ? 'rgba(224,146,47,0.1)' : 'rgba(46,139,111,0.1)';
  return (
    <div style={{ display: 'flex', alignItems: 'center', gap: 13, background: '#fff', borderRadius: 14, border: '1px solid ' + T.line2, padding: '14px 18px' }}>
      <div style={{ width: 38, height: 38, borderRadius: 10, background: bg, display: 'flex', alignItems: 'center', justifyContent: 'center', flexShrink: 0 }}>
        <Icon name={pending ? 'clock' : 'checkC'} size={20} color={c} stroke={2} />
      </div>
      <div style={{ flex: 1 }}>
        <div style={{ fontFamily: FB, fontWeight: 700, fontSize: 13.5, color: T.ink }}>Payment · prepaid</div>
        <div style={{ fontFamily: FB, fontSize: 12, color: T.muted, marginTop: 1 }}>
          {pending ? 'Price confirms within ~1 business hour, then prepay to release the booking.' : 'Paid in full before sailing — no balance owing. Charges (if any) passed at cost.'}
        </div>
      </div>
      <span style={{ fontFamily: FM, fontSize: 10.5, fontWeight: 700, color: c, background: bg, padding: '5px 11px', borderRadius: 999, letterSpacing: 0.3, textTransform: 'uppercase' }}>{pending ? 'Awaiting price' : 'Paid in full'}</span>
    </div>
  );
}

Object.assign(window, { ComplianceStep, complianceValid, EstimateExtras, complianceDocsFor, quotePrice, ReviewSignPay, reviewValid, PaymentBar });
