/* Shared dashboard utilities — live numbers, toasts, modals, command palette */

/* ===== Live number hook ===== */
const useLiveNumber = (initial, opts = {}) => {
  const {
    interval = 1400 + Math.random() * 1000,
    delta = 1,
    min = -Infinity,
    max =  Infinity,
    decimals = 0,
  } = opts;
  const [v, setV] = React.useState(initial);
  React.useEffect(() => {
    const id = setInterval(() => {
      setV(prev => {
        const d = (Math.random() * 2 - 1) * delta;
        let next = prev + d;
        if (next < min) next = min + Math.random() * delta;
        if (next > max) next = max - Math.random() * delta;
        return Number(next.toFixed(decimals));
      });
    }, interval);
    return () => clearInterval(id);
  }, []);
  return v;
};

const fmt = (n, decimals = 0) => Number(n).toLocaleString('en-US', {
  minimumFractionDigits: decimals,
  maximumFractionDigits: decimals,
});

/* ===== App state context (shared between desktop + mobile-like layers) ===== */
const AppCtx = React.createContext(null);
let toastId = 0;

const AppProvider = ({ children, scoped = false }) => {
  const [toasts, setToasts] = React.useState([]);
  const [modal, setModal] = React.useState(null);

  const toast = React.useCallback((opts) => {
    const id = ++toastId;
    const t = typeof opts === 'string' ? { msg: opts } : opts;
    setToasts(arr => [...arr, { id, ...t }]);
    setTimeout(() => {
      setToasts(arr => arr.filter(x => x.id !== id));
    }, t.duration || 3200);
  }, []);

  const openModal = React.useCallback((m) => setModal(m), []);
  const closeModal = React.useCallback(() => setModal(null), []);

  React.useEffect(() => {
    const onKey = (e) => {
      if ((e.metaKey || e.ctrlKey) && e.key === 'k') {
        e.preventDefault();
        openModal({ kind: 'cmdk' });
      }
      if (e.key === 'Escape') closeModal();
    };
    window.addEventListener('keydown', onKey);
    return () => window.removeEventListener('keydown', onKey);
  }, [openModal, closeModal]);

  return (
    <AppCtx.Provider value={{ toast, openModal, closeModal, modal }}>
      {children}
      <Toaster toasts={toasts}/>
      <ModalHost modal={modal} close={closeModal}/>
    </AppCtx.Provider>
  );
};
const useApp = () => React.useContext(AppCtx);

/* ===== Toaster ===== */
const Toaster = ({ toasts }) => (
  <div className="app-toaster">
    {toasts.map(t => (
      <div key={t.id} className={"app-toast " + (t.tone || 'ok')}>
        <span className="app-toast-ico">
          {t.tone === 'warn' ? <IconBolt size={13}/> :
           t.tone === 'err'  ? <IconClose size={13}/> :
                               <IconCheck size={13}/>}
        </span>
        <div className="app-toast-body">
          {t.title && <strong>{t.title}</strong>}
          <span>{t.msg}</span>
        </div>
      </div>
    ))}
  </div>
);

/* ===== Modal host ===== */
const ModalHost = ({ modal, close }) => {
  if (!modal) return null;
  return (
    <div className="app-modal-host" onMouseDown={(e) => { if (e.target === e.currentTarget) close(); }}>
      <div className={"app-modal " + (modal.kind || '')}>
        {modal.kind === 'cmdk'    && <CommandPalette close={close}/>}
        {modal.kind === 'notifs'  && <NotifPanel close={close}/>}
        {modal.kind === 'deploy'  && <DeployModal close={close} target={modal.target}/>}
        {modal.kind === 'detail'  && <DetailPanel close={close} item={modal.item}/>}
        {modal.kind === 'newproj' && <NewProject close={close}/>}
      </div>
    </div>
  );
};

/* ===== Command palette ===== */
const CMD_ITEMS = [
  { k: 'cmd1', label: 'Go to · Overview',         hint: '↩',   ico: <IconHome size={13}/>,  action: (app) => app.toast('Switched to Overview') },
  { k: 'cmd2', label: 'Go to · AI Systems',       hint: 'A',   ico: <IconBrain size={13}/>, action: (app) => app.toast('Switched to AI Systems') },
  { k: 'cmd3', label: 'Go to · Blockchain',       hint: 'B',   ico: <IconNetwork size={13}/>, action: (app) => app.toast('Switched to Blockchain') },
  { k: 'cmd4', label: 'New project…',             hint: 'N',   ico: <IconPlus size={13}/>,  action: (app) => app.openModal({ kind: 'newproj' }) },
  { k: 'cmd5', label: 'Deploy current module',    hint: 'D',   ico: <IconRocket size={13}/>, action: (app) => app.openModal({ kind: 'deploy', target: 'brainfy-prod' }) },
  { k: 'cmd6', label: 'Invite teammate',          hint: '@',   ico: <IconUsers size={13}/>, action: (app) => app.toast('Invite link copied') },
  { k: 'cmd7', label: 'Open Kath AI assistant',   hint: '?',   ico: <IconSparkle size={13}/>, action: (app) => app.toast('Kath AI · use the bubble at bottom-right') },
];
const CommandPalette = ({ close }) => {
  const app = useApp();
  const [q, setQ] = React.useState('');
  const inputRef = React.useRef(null);
  React.useEffect(() => { inputRef.current?.focus(); }, []);
  const filtered = CMD_ITEMS.filter(i => i.label.toLowerCase().includes(q.toLowerCase()));
  return (
    <div className="cmdk">
      <div className="cmdk-input">
        <IconSearch size={14}/>
        <input
          ref={inputRef}
          value={q}
          onChange={(e) => setQ(e.target.value)}
          placeholder="Type a command or search…"
        />
        <kbd>ESC</kbd>
      </div>
      <div className="cmdk-list">
        {filtered.length === 0 && <div className="cmdk-empty">No results for "{q}"</div>}
        {filtered.map(i => (
          <button
            key={i.k}
            className="cmdk-item"
            onClick={() => { i.action(app); close(); }}
          >
            <span className="cmdk-ico">{i.ico}</span>
            <span className="cmdk-label">{i.label}</span>
            <kbd>{i.hint}</kbd>
          </button>
        ))}
      </div>
      <div className="cmdk-foot">
        <span><kbd>↑↓</kbd> navigate</span>
        <span><kbd>↩</kbd> select</span>
        <span><kbd>ESC</kbd> close</span>
      </div>
    </div>
  );
};

/* ===== Notifications panel ===== */
const NOTIFS = [
  { sev: 'ok',   t: 'Brainfy v2.4.1 deployed',     m: 'us-east-1 · 2 min ago' },
  { sev: 'info', t: 'New AI agent created',         m: 'kath-ai · 7 min ago' },
  { sev: 'warn', t: 'Asbel Rock awaiting review',   m: 'eu-central · 14 min ago' },
  { sev: 'ok',   t: 'XDX block #4,892,113 finalized',m: 'global · 18 min ago' },
  { sev: 'info', t: '12 new sign-ups today',        m: 'web · 22 min ago' },
];
const NotifPanel = ({ close }) => {
  const app = useApp();
  return (
    <div className="notif-panel">
      <header className="notif-head">
        <strong>Notifications</strong>
        <button className="notif-mark" onClick={() => { app.toast('All marked as read'); close(); }}>Mark all read</button>
      </header>
      <div className="notif-list">
        {NOTIFS.map((n, i) => (
          <button key={i} className="notif-row" onClick={() => { app.toast({ msg: n.t, tone: n.sev === 'warn' ? 'warn' : 'ok' }); close(); }}>
            <span className={"notif-sev " + n.sev}/>
            <div>
              <div className="notif-t">{n.t}</div>
              <div className="notif-m">{n.m}</div>
            </div>
          </button>
        ))}
      </div>
      <footer className="notif-foot">
        <button onClick={close}>Close</button>
      </footer>
    </div>
  );
};

/* ===== Deploy modal ===== */
const DEPLOY_STEPS = [
  'Compiling modules…',
  'Running integration tests…',
  'Uploading artifact…',
  'Syncing infrastructure…',
  'Booting region us-east-1…',
  'Smoke tests passing…',
  'Live · Booster X synced.',
];
const DeployModal = ({ close, target }) => {
  const [step, setStep] = React.useState(0);
  const app = useApp();
  React.useEffect(() => {
    if (step >= DEPLOY_STEPS.length) return;
    const id = setTimeout(() => setStep(s => s + 1), 700);
    return () => clearTimeout(id);
  }, [step]);
  const done = step >= DEPLOY_STEPS.length;
  return (
    <div className="deploy">
      <header className="deploy-head">
        <span className="deploy-ico"><IconRocket size={16}/></span>
        <div>
          <div className="deploy-title">{done ? 'Deployed' : 'Deploying'} · {target || 'module'}</div>
          <div className="deploy-sub">Powered by Booster X execution layer</div>
        </div>
        <button className="deploy-close" onClick={close}><IconClose size={13}/></button>
      </header>
      <div className="deploy-progress"><i style={{ width: Math.min(100, (step / DEPLOY_STEPS.length) * 100) + '%' }}/></div>
      <ol className="deploy-steps">
        {DEPLOY_STEPS.map((txt, i) => (
          <li key={i} className={i < step ? 'done' : i === step ? 'active' : ''}>
            <span className="deploy-step-bullet">
              {i < step ? <IconCheck size={10}/> : i === step ? <span className="deploy-step-spin"/> : null}
            </span>
            <span>{txt}</span>
          </li>
        ))}
      </ol>
      {done && (
        <div className="deploy-actions">
          <button className="deploy-btn ghost" onClick={close}>Close</button>
          <button className="deploy-btn primary" onClick={() => { app.toast({ title: 'Deployment shared', msg: 'Link copied to clipboard' }); close(); }}>
            <IconExternal size={12}/> Share
          </button>
        </div>
      )}
    </div>
  );
};

/* ===== Detail panel (for KPI / module / row click) ===== */
const DetailPanel = ({ close, item }) => {
  const live = useLiveNumber(item.value || 1000, { delta: 30, min: 0, max: 99999 });
  return (
    <div className="detail">
      <header className="detail-head">
        <div>
          <div className="detail-eyebrow">{item.eyebrow}</div>
          <div className="detail-title">{item.title}</div>
        </div>
        <button className="deploy-close" onClick={close}><IconClose size={13}/></button>
      </header>
      <div className="detail-stat">
        <div className="detail-val live">{fmt(live)}</div>
        <div className="detail-delta">{item.delta}</div>
      </div>
      <div className="detail-rows">
        {(item.rows || []).map((r, i) => (
          <div key={i} className="detail-row">
            <span>{r.label}</span>
            <strong>{r.value}</strong>
          </div>
        ))}
      </div>
      <button className="deploy-btn primary" style={{width:'100%'}} onClick={close}>Got it</button>
    </div>
  );
};

/* ===== New Project (mini wizard) ===== */
const NewProject = ({ close }) => {
  const app = useApp();
  const [name, setName] = React.useState('');
  const [kind, setKind] = React.useState('ai');
  const submit = () => {
    if (!name.trim()) {
      app.toast({ msg: 'Give your project a name', tone: 'warn' });
      return;
    }
    app.toast({ title: 'Project created', msg: `${name} · ${kind.toUpperCase()}` });
    close();
  };
  return (
    <div className="newproj">
      <header className="detail-head">
        <div>
          <div className="detail-eyebrow">CREATE</div>
          <div className="detail-title">New project</div>
        </div>
        <button className="deploy-close" onClick={close}><IconClose size={13}/></button>
      </header>
      <label className="np-label">Project name</label>
      <input className="np-input" autoFocus value={name} onChange={e => setName(e.target.value)} placeholder="e.g. Brainfy v3"/>
      <label className="np-label">Type</label>
      <div className="np-kind">
        {[
          { k: 'ai', l: 'AI Product', ico: <IconBrain size={13}/> },
          { k: 'web4', l: 'Web4 App', ico: <IconNetwork size={13}/> },
          { k: 'chain', l: 'Blockchain', ico: <IconBox size={13}/> },
          { k: 'infra', l: 'Infrastructure', ico: <IconCloud size={13}/> },
        ].map(o => (
          <button key={o.k} className={"np-opt" + (kind === o.k ? ' active' : '')} onClick={() => setKind(o.k)}>
            {o.ico} {o.l}
          </button>
        ))}
      </div>
      <div className="deploy-actions">
        <button className="deploy-btn ghost" onClick={close}>Cancel</button>
        <button className="deploy-btn primary" onClick={submit}>
          <IconPlus size={12}/> Create project
        </button>
      </div>
    </div>
  );
};

Object.assign(window, {
  useLiveNumber, fmt,
  AppCtx, AppProvider, useApp,
  Toaster, ModalHost, CommandPalette, NotifPanel, DeployModal, DetailPanel, NewProject,
});
