/* ============================================================
   AppData.jsx — conteúdo dos módulos + atoms refinados de UI
   Visual SaaS premium, dark, minimalista. Cada módulo traz
   conteúdo para 3 papéis distintos: web (completo), tablet
   (intermediário) e mobile (compacto).
   ============================================================ */

/* paleta interna das telas */
const SC = {
  bg: '#080C16', panel: '#0C1220', panel2: '#0E1424',
  line: 'rgba(255,255,255,0.06)', lineStrong: 'rgba(255,255,255,0.10)',
  text: '#EDF1FA', mut: '#8A93AB', dim: '#5C6680',
  cyan: '#00D4FF', blue: '#005EFF', green: '#1FD17B', amber: '#FFB020', red: '#FF5A6B',
};

/* ---------- dados dos módulos ---------- */
const AR_MODULES = [
  {
    id: 'gestao', label: 'Gestão', icon: 'layout-dashboard', accent: '#00D4FF',
    page: 'Painel executivo', web: 'chart',
    kpis: [
      { l: 'Receita do mês', v: 'R$ 284,9k', d: '+12,4%', up: true },
      { l: 'Pedidos', v: '1.842', d: '+8,1%', up: true },
      { l: 'Ticket médio', v: 'R$ 154', d: '+3,0%', up: true },
      { l: 'NPS', v: '72', d: '+6', up: true },
    ],
    chartTitle: 'Receita reconhecida', chartHint: 'últimos 6 meses',
    series: [42, 51, 47, 63, 70, 88], labels: ['Jan', 'Fev', 'Mar', 'Abr', 'Mai', 'Jun'],
    ai: 'Projeção de R$ 312k para o próximo mês (+9%). Reforce o estoque das 3 categorias de maior giro.',
    aiAction: 'Ver plano sugerido',
    listTitle: 'Prioridades de hoje',
    list: [
      ['circle-check', 'Aprovar 3 pedidos acima de R$ 10k', 'aprovar'],
      ['triangle-alert', '12 SKUs abaixo do ponto de pedido', 'estoque'],
      ['calendar-clock', 'Fechamento financeiro em 2 dias', 'prazo'],
    ],
    ring: { label: 'Meta do mês', pct: 87, sub: 'R$ 284,9k de R$ 327k' },
    hero: { l: 'Receita do mês', v: 'R$ 284,9k', d: '+12,4%', up: true, sub: 'vs. mês anterior' },
  },
  {
    id: 'atendimento', label: 'Atendimento', icon: 'headset', accent: '#00D4FF',
    page: 'CRM · Atendimento', web: 'pipeline',
    kpis: [
      { l: 'Atendimentos hoje', v: '327', d: '+18%', up: true },
      { l: 'Tempo médio', v: '1m 12s', d: '-22%', up: true },
      { l: 'Resolvido pela IA', v: '78%', d: '+6 p.p.', up: true },
      { l: 'CSAT', v: '4,8', d: '+0,3', up: true },
    ],
    pipeline: [
      { stage: 'Novo lead', count: 24, cards: [['MS', 'Mercado São João', 'R$ 8,2k']] },
      { stage: 'Qualificação', count: 18, cards: [['VC', 'Vera Cruz', 'R$ 14k']] },
      { stage: 'Em atendimento', count: 12, cards: [['LA', 'Loja Aurora', 'R$ 6,4k']] },
      { stage: 'Proposta', count: 9, cards: [['TP', 'Tech Ponto', 'R$ 21k']] },
      { stage: 'Fechado', count: 15, cards: [['DF', 'Dist. Farol', 'R$ 11k']] },
    ],
    series: [8, 14, 22, 31, 27, 19, 24, 33, 21], labels: ['8h', '11h', '14h', '17h', '20h'],
    chartTitle: 'Volume por hora', chartHint: 'hoje',
    ai: 'Priorizei 6 oportunidades com alta intenção de compra e sugeri follow-up para 3 propostas paradas há 48h.',
    aiAction: 'Distribuir para o time',
    listTitle: 'Fila em tempo real',
    list: [
      ['user', 'Ana Prado · 2ª via de boleto', 'IA'],
      ['user', 'Construtora Vera Cruz · suporte', 'quente'],
      ['user', 'Loja Aurora · orçamento', 'aguardando'],
    ],
    ring: { label: 'Resolvido pela IA', pct: 78, sub: '255 de 327 atendimentos' },
    hero: { l: 'Na fila agora', v: '8', d: 'SLA 2m', up: true, sub: '3 priorizados pela IA' },
  },
  {
    id: 'financeiro', label: 'Financeiro', icon: 'wallet', accent: '#1FD17B',
    page: 'Financeiro', web: 'cashflow',
    kpis: [
      { l: 'A receber', v: 'R$ 96,2k', d: '+4%', up: true },
      { l: 'A pagar', v: 'R$ 41,8k', d: '-9%', up: true },
      { l: 'Saldo projetado', v: 'R$ 212k', d: '+11%', up: true },
      { l: 'Inadimplência', v: '2,1%', d: '-0,4 p.p.', up: true },
    ],
    series: [60, 72, 65, 80, 76, 92], series2: [38, 41, 44, 39, 42, 40], labels: ['S1', 'S2', 'S3', 'S4', 'S5', 'S6'],
    chartTitle: 'Entradas x saídas', chartHint: '6 semanas',
    ai: 'Fluxo positivo nas próximas 4 semanas. Antecipar 2 pagamentos com desconto economiza R$ 3,2k em juros.',
    aiAction: 'Aplicar sugestão',
    listTitle: 'Contas a vencer',
    list: [
      ['file-text', 'Fornecedor Atlas · R$ 12.400', '2 dias'],
      ['file-text', 'Energia · R$ 3.180', '4 dias'],
      ['file-text', 'Folha de pagamento · R$ 21.900', '5 dias'],
    ],
    ring: { label: 'Margem líquida', pct: 34, sub: '+2,3 p.p. no mês' },
    hero: { l: 'Saldo projetado', v: 'R$ 212k', d: '+11%', up: true, sub: 'próximos 30 dias' },
  },
  {
    id: 'estoque', label: 'Estoque', icon: 'package', accent: '#FFB020',
    page: 'Estoque & Suprimentos', web: 'bars',
    kpis: [
      { l: 'SKUs ativos', v: '1.204', d: '+5%', up: true },
      { l: 'Em falta', v: '18', d: '-7', up: true },
      { l: 'Giro médio', v: '4,2x', d: '+0,3', up: true },
      { l: 'Valor em estoque', v: 'R$ 487k', d: '+2%', up: true },
    ],
    series: [78, 54, 91, 33, 67, 48], labels: ['Bebidas', 'Limpeza', 'Higiene', 'Mercearia', 'Frios', 'Padaria'],
    chartTitle: 'Nível por categoria', chartHint: '% do ideal',
    ai: '12 itens abaixo do ponto de pedido. Gerei uma ordem de compra com base na previsão de demanda.',
    aiAction: 'Revisar ordem de compra',
    listTitle: 'Reposição prioritária',
    list: [
      ['package', 'Café torrado 500g · 6 un.', 'crítico'],
      ['package', 'Detergente 5L · 11 un.', 'baixo'],
      ['package', 'Arroz 5kg · 4 un.', 'crítico'],
    ],
    ring: { label: 'Cobertura de estoque', pct: 68, sub: '~21 dias de venda' },
    hero: { l: 'Itens para repor', v: '12', d: 'ordem pronta', up: true, sub: 'sugerido pela IA' },
  },
  {
    id: 'vendas', label: 'Vendas', icon: 'trending-up', accent: '#00D4FF',
    page: 'Comercial & Vendas', web: 'funnel',
    funnel: [
      { stage: 'Visitantes', v: '8.400', pct: 100 },
      { stage: 'Leads', v: '1.260', pct: 64 },
      { stage: 'Qualificados', v: '470', pct: 41 },
      { stage: 'Propostas', v: '138', pct: 24 },
      { stage: 'Fechados', v: '47', pct: 13 },
    ],
    kpis: [
      { l: 'Faturamento', v: 'R$ 318k', d: '+15%', up: true },
      { l: 'Conversão', v: '3,4%', d: '+0,6 p.p.', up: true },
      { l: 'Oportunidades', v: '214', d: '+22%', up: true },
      { l: 'Meta atingida', v: '87%', d: '+9 p.p.', up: true },
    ],
    series: [55, 62, 58, 74, 81, 96], labels: ['S1', 'S2', 'S3', 'S4', 'S5', 'S6'],
    chartTitle: 'Faturamento semanal', chartHint: '6 semanas',
    ai: 'Identifiquei 23 leads quentes (68% de probabilidade de fechamento) e sugiro uma campanha para 312 carrinhos abandonados.',
    aiAction: 'Criar campanha',
    listTitle: 'Oportunidades em destaque',
    list: [
      ['briefcase', 'Vera Cruz · proposta enviada', '68%'],
      ['briefcase', 'Loja Aurora · negociação', '54%'],
      ['briefcase', 'Tech Ponto · follow-up', '41%'],
    ],
    ring: { label: 'Meta do mês', pct: 87, sub: 'R$ 318k de R$ 365k' },
    hero: { l: 'Faturamento no mês', v: 'R$ 318k', d: '+15%', up: true, sub: '87% da meta' },
  },
  {
    id: 'rh', label: 'RH', icon: 'users', accent: '#7CB0FF',
    page: 'Pessoas & Cultura', web: 'chart',
    kpis: [
      { l: 'Colaboradores', v: '86', d: '+4', up: true },
      { l: 'Admissões no mês', v: '5', d: '+2', up: true },
      { l: 'Turnover', v: '4,0%', d: '-0,8 p.p.', up: true },
      { l: 'eNPS', v: '72', d: '+6', up: true },
    ],
    series: [70, 73, 75, 79, 82, 86], labels: ['Jan', 'Fev', 'Mar', 'Abr', 'Mai', 'Jun'],
    chartTitle: 'Headcount', chartHint: 'últimos 6 meses',
    ai: 'Triei 140 currículos e indiquei 8 candidatos para Vendedor Pleno. 2 colaboradores em risco de turnover.',
    aiAction: 'Ver recomendações',
    listTitle: 'Agenda de pessoas',
    list: [
      ['user-round', 'Vendedor Pleno · 8 finalistas', 'entrevista'],
      ['graduation-cap', 'Treinamento de IA · 24 inscritos', 'hoje'],
      ['calendar', 'Avaliações de desempenho', 'esta semana'],
    ],
    ring: { label: 'Clima organizacional', pct: 84, sub: 'eNPS 72 · ótimo' },
    hero: { l: 'Colaboradores ativos', v: '86', d: '+4', up: true, sub: '5 admissões no mês' },
  },
];

/* ---------- helpers ---------- */
const tagStyle = (s) => {
  s = String(s).toLowerCase();
  if (['crítico', 'urgente', 'atrasado'].includes(s)) return { c: SC.red, bg: 'rgba(255,90,107,0.12)', bd: 'rgba(255,90,107,0.28)' };
  if (['ia', 'aprovar', 'fechado'].includes(s)) return { c: SC.cyan, bg: 'rgba(0,212,255,0.12)', bd: 'rgba(0,212,255,0.28)' };
  if (['baixo', 'aguardando', 'prazo', 'hoje', 'estoque'].includes(s)) return { c: SC.amber, bg: 'rgba(255,176,32,0.12)', bd: 'rgba(255,176,32,0.28)' };
  if (['quente', 'entrevista'].includes(s)) return { c: '#FF8A5B', bg: 'rgba(255,138,91,0.12)', bd: 'rgba(255,138,91,0.28)' };
  return { c: SC.green, bg: 'rgba(31,209,123,0.12)', bd: 'rgba(31,209,123,0.28)' };
};

const Tag = ({ children, sm }) => {
  const s = tagStyle(children);
  return <span style={{ fontFamily: 'var(--ar-font-body)', fontSize: sm ? 9 : 10, fontWeight: 600, color: s.c, background: s.bg, border: `1px solid ${s.bd}`, borderRadius: 6, padding: sm ? '1px 6px' : '2px 8px', whiteSpace: 'nowrap', letterSpacing: '0.01em' }}>{children}</span>;
};

const Delta = ({ d, up, size = 10.5 }) => (
  <span style={{ display: 'inline-flex', alignItems: 'center', gap: 1, fontFamily: 'var(--ar-font-body)', fontSize: size, fontWeight: 600, color: up ? SC.green : SC.red, whiteSpace: 'nowrap' }}>
    <i data-lucide={up ? 'trending-up' : 'trending-down'} style={{ width: size, height: size }}></i>{d}
  </span>
);

/* área/linha — discreta */
const Area = ({ data, w = 320, h = 92, color = '#00D4FF', uid = 'a', secondary, pad = 6 }) => {
  const all = secondary ? data.concat(secondary) : data;
  const max = Math.max(...all), min = Math.min(...all);
  const nx = i => pad + (i / (data.length - 1)) * (w - pad * 2);
  const ny = v => h - pad - ((v - min) / ((max - min) || 1)) * (h - pad * 2 - 4);
  const ln = a => a.map((v, i) => `${nx(i).toFixed(1)},${ny(v).toFixed(1)}`).join(' ');
  return (
    <svg viewBox={`0 0 ${w} ${h}`} preserveAspectRatio="none" width="100%" height="100%" style={{ display: 'block', overflow: 'hidden' }}>
      <defs>
        <linearGradient id={'ar' + uid} x1="0" y1="0" x2="0" y2="1">
          <stop offset="0%" stopColor={color} stopOpacity="0.26" /><stop offset="100%" stopColor={color} stopOpacity="0" />
        </linearGradient>
      </defs>
      <polygon points={`${pad},${h - pad} ${ln(data)} ${w - pad},${h - pad}`} fill={`url(#ar${uid})`} />
      {secondary && <polyline points={ln(secondary)} fill="none" stroke={SC.amber} strokeWidth="1.4" strokeDasharray="3 4" opacity="0.8" strokeLinecap="round" vectorEffect="non-scaling-stroke" />}
      <polyline points={ln(data)} fill="none" stroke={color} strokeWidth="2" strokeLinejoin="round" strokeLinecap="round" vectorEffect="non-scaling-stroke" />
    </svg>
  );
};

const Bars = ({ data, w = 320, h = 92, pad = 6, uid = 'b' }) => {
  const max = Math.max(...data); const bw = (w - pad * 2) / data.length;
  return (
    <svg viewBox={`0 0 ${w} ${h}`} preserveAspectRatio="none" width="100%" height="100%" style={{ display: 'block', overflow: 'hidden' }}>
      <defs><linearGradient id={'bg' + uid} x1="0" y1="0" x2="0" y2="1"><stop offset="0%" stopColor="#00D4FF" /><stop offset="100%" stopColor="#005EFF" /></linearGradient></defs>
      {data.map((v, i) => { const bh = (v / max) * (h - pad * 2); return <rect key={i} x={pad + i * bw + bw * 0.30} y={h - pad - bh} width={bw * 0.40} height={bh} rx="2" fill={`url(#bg${uid})`} opacity={0.5 + 0.5 * (v / max)} />; })}
    </svg>
  );
};

/* anel de progresso */
const Ring = ({ pct, size = 86, stroke = 8, uid = 'r', label, value }) => {
  const r = (size - stroke) / 2, c = 2 * Math.PI * r, off = c * (1 - pct / 100);
  return (
    <div style={{ position: 'relative', width: size, height: size, flexShrink: 0 }}>
      <svg width={size} height={size} style={{ transform: 'rotate(-90deg)' }}>
        <defs><linearGradient id={'rg' + uid} x1="0" y1="0" x2="1" y2="1"><stop offset="0%" stopColor="#00D4FF" /><stop offset="100%" stopColor="#005EFF" /></linearGradient></defs>
        <circle cx={size / 2} cy={size / 2} r={r} fill="none" stroke="rgba(255,255,255,0.08)" strokeWidth={stroke} />
        <circle cx={size / 2} cy={size / 2} r={r} fill="none" stroke={`url(#rg${uid})`} strokeWidth={stroke} strokeLinecap="round" strokeDasharray={c} strokeDashoffset={off} />
      </svg>
      <div style={{ position: 'absolute', inset: 0, display: 'flex', flexDirection: 'column', alignItems: 'center', justifyContent: 'center' }}>
        <div style={{ fontFamily: 'var(--ar-font-title)', fontWeight: 700, fontSize: size * 0.26, color: SC.text, lineHeight: 1 }}>{value || pct + '%'}</div>
        {label && <div style={{ fontFamily: 'var(--ar-font-body)', fontSize: size * 0.105, color: SC.mut, marginTop: 3 }}>{label}</div>}
      </div>
    </div>
  );
};

/* célula KPI */
const Kpi = ({ k, pad = '11px 13px' }) => (
  <div style={{ background: SC.panel, border: `1px solid ${SC.line}`, borderRadius: 11, padding: pad, minWidth: 0 }}>
    <div style={{ fontFamily: 'var(--ar-font-body)', fontSize: 10.5, color: SC.mut, fontWeight: 500, whiteSpace: 'nowrap', overflow: 'hidden', textOverflow: 'ellipsis' }}>{k.l}</div>
    <div style={{ display: 'flex', alignItems: 'baseline', justifyContent: 'space-between', gap: 5, marginTop: 6, flexWrap: 'wrap' }}>
      <span style={{ fontFamily: 'var(--ar-font-title)', fontWeight: 700, fontSize: 18, color: SC.text, letterSpacing: '-0.01em', whiteSpace: 'nowrap' }}>{k.v}</span>
      <Delta d={k.d} up={k.up} size={9.5} />
    </div>
  </div>
);

/* card de recomendação da IA — elegante e discreto */
const AIBlock = ({ m, compact, lines }) => (
  <div style={{ position: 'relative', borderRadius: 13, padding: compact ? '12px 13px' : '14px 15px', background: 'linear-gradient(150deg, rgba(0,94,255,0.10), rgba(0,212,255,0.03))', border: '1px solid rgba(0,212,255,0.22)', overflow: 'hidden' }}>
    <div style={{ position: 'absolute', top: -34, right: -22, width: 90, height: 90, borderRadius: 999, background: 'radial-gradient(circle, rgba(0,212,255,0.16), transparent 70%)' }} />
    <div style={{ display: 'flex', alignItems: 'center', gap: 7, position: 'relative' }}>
      <div style={{ width: 20, height: 20, borderRadius: 6, background: 'linear-gradient(135deg,#005EFF,#00D4FF)', display: 'flex', alignItems: 'center', justifyContent: 'center', color: '#fff', flexShrink: 0 }}>
        <i data-lucide="sparkles" style={{ width: 12, height: 12 }}></i>
      </div>
      <span style={{ fontFamily: 'var(--ar-font-body)', fontSize: 10, fontWeight: 700, letterSpacing: '0.1em', textTransform: 'uppercase', color: '#86E5FF' }}>Recomendação da IA</span>
    </div>
    <p style={{ position: 'relative', fontFamily: 'var(--ar-font-body)', fontSize: compact ? 10.5 : 11.5, lineHeight: 1.45, color: '#CBD6EE', margin: compact ? '7px 0 9px' : '9px 0 11px', display: '-webkit-box', WebkitLineClamp: lines || (compact ? 3 : 4), WebkitBoxOrient: 'vertical', overflow: 'hidden' }}>{m.ai}</p>
    <button style={{ position: 'relative', fontFamily: 'var(--ar-font-body)', fontSize: 11, fontWeight: 600, color: '#86E5FF', background: 'rgba(0,212,255,0.08)', border: '1px solid rgba(0,212,255,0.3)', borderRadius: 8, padding: '6px 11px', display: 'inline-flex', alignItems: 'center', gap: 6, cursor: 'pointer' }}>
      {m.aiAction}<i data-lucide="arrow-right" style={{ width: 12, height: 12 }}></i>
    </button>
  </div>
);

/* lista compacta */
const Rows = ({ m, n = 3, compact }) => (
  <div style={{ display: 'flex', flexDirection: 'column', gap: compact ? 7 : 9 }}>
    {m.list.slice(0, n).map((row, i) => (
      <div key={i} style={{ display: 'flex', alignItems: 'center', gap: 9 }}>
        <div style={{ width: compact ? 24 : 28, height: compact ? 24 : 28, borderRadius: 7, background: 'rgba(0,212,255,0.07)', border: '1px solid rgba(0,212,255,0.18)', display: 'flex', alignItems: 'center', justifyContent: 'center', color: SC.cyan, flexShrink: 0 }}>
          <i data-lucide={row[0]} style={{ width: compact ? 12 : 14, height: compact ? 12 : 14 }}></i>
        </div>
        <div style={{ flex: 1, fontFamily: 'var(--ar-font-body)', fontSize: compact ? 11 : 12.5, color: '#C2CCE2', overflow: 'hidden', whiteSpace: 'nowrap', textOverflow: 'ellipsis' }}>{row[1]}</div>
        <Tag sm={compact}>{row[2]}</Tag>
      </div>
    ))}
  </div>
);

/* pipeline kanban (web · atendimento) */
const Pipeline = ({ m }) => (
  <div style={{ display: 'grid', gridTemplateColumns: `repeat(${m.pipeline.length}, 1fr)`, gap: 8, height: '100%' }}>
    {m.pipeline.map((col, i) => (
      <div key={i} style={{ background: SC.panel, border: `1px solid ${SC.line}`, borderRadius: 10, padding: '9px 8px', display: 'flex', flexDirection: 'column', gap: 6, minWidth: 0, overflow: 'hidden' }}>
        <div style={{ display: 'flex', alignItems: 'center', justifyContent: 'space-between' }}>
          <span style={{ fontFamily: 'var(--ar-font-body)', fontSize: 9.5, fontWeight: 600, color: SC.mut, whiteSpace: 'nowrap', overflow: 'hidden', textOverflow: 'ellipsis' }}>{col.stage}</span>
          <span style={{ fontFamily: 'var(--ar-font-title)', fontSize: 10, fontWeight: 700, color: i === m.pipeline.length - 1 ? SC.green : SC.cyan, background: 'rgba(255,255,255,0.04)', borderRadius: 999, padding: '1px 6px' }}>{col.count}</span>
        </div>
        {col.cards.map((c, j) => (
          <div key={j} style={{ background: SC.panel2, border: `1px solid ${SC.line}`, borderRadius: 8, padding: '7px 8px' }}>
            <div style={{ display: 'flex', alignItems: 'center', gap: 6 }}>
              <div style={{ width: 18, height: 18, borderRadius: 5, background: 'linear-gradient(135deg,#1a2238,#10182B)', border: '1px solid rgba(0,212,255,0.25)', display: 'flex', alignItems: 'center', justifyContent: 'center', fontFamily: 'var(--ar-font-title)', fontSize: 7.5, fontWeight: 700, color: SC.cyan }}>{c[0]}</div>
              <span style={{ fontFamily: 'var(--ar-font-body)', fontSize: 9.5, color: SC.text, overflow: 'hidden', whiteSpace: 'nowrap', textOverflow: 'ellipsis' }}>{c[1]}</span>
            </div>
            <div style={{ display: 'flex', alignItems: 'center', justifyContent: 'space-between', marginTop: 6 }}>
              <span style={{ fontFamily: 'var(--ar-font-title)', fontSize: 11, fontWeight: 700, color: SC.text }}>{c[2]}</span>
              <span style={{ width: 14, height: 3, borderRadius: 999, background: i === m.pipeline.length - 1 ? SC.green : 'linear-gradient(90deg,#005EFF,#00D4FF)' }} />
            </div>
          </div>
        ))}
        <div style={{ fontFamily: 'var(--ar-font-body)', fontSize: 8.5, color: SC.dim, textAlign: 'center', marginTop: 'auto' }}>+{col.count - col.cards.length} no estágio</div>
      </div>
    ))}
  </div>
);

/* funil (web · vendas) */
const Funnel = ({ m }) => (
  <div style={{ display: 'flex', flexDirection: 'column', height: '100%', justifyContent: 'center', gap: 7 }}>
    {m.funnel.map((f, i) => (
      <div key={i} style={{ flex: 1, minHeight: 20, maxHeight: 34, display: 'flex', alignItems: 'center', gap: 11 }}>
        <span style={{ width: 78, fontFamily: 'var(--ar-font-body)', fontSize: 10.5, color: SC.mut, textAlign: 'right', flexShrink: 0, whiteSpace: 'nowrap' }}>{f.stage}</span>
        <div style={{ flex: 1, height: 16, borderRadius: 5, background: SC.panel, position: 'relative', overflow: 'hidden' }}>
          <div style={{ position: 'absolute', inset: 0, width: f.pct + '%', borderRadius: 5, background: 'linear-gradient(90deg, rgba(0,94,255,0.92), rgba(0,212,255,0.88))', boxShadow: '0 0 14px rgba(0,212,255,0.22)' }} />
          <span style={{ position: 'absolute', left: 9, top: 0, bottom: 0, display: 'flex', alignItems: 'center', fontFamily: 'var(--ar-font-title)', fontSize: 9.5, fontWeight: 700, color: '#fff' }}>{f.v}</span>
        </div>
        <span style={{ width: 30, fontFamily: 'var(--ar-font-body)', fontSize: 10, fontWeight: 600, color: SC.cyan, flexShrink: 0, textAlign: 'right' }}>{f.pct}%</span>
      </div>
    ))}
  </div>
);

/* gráfico genérico por tipo */
const ModuleChart = ({ m, w, h, uid }) => {
  if (m.web === 'cashflow' || m.id === 'financeiro') return <Area data={m.series} secondary={m.series2} w={w} h={h} uid={uid} color={SC.green} />;
  if (m.web === 'bars' || m.id === 'estoque') return <Bars data={m.series} w={w} h={h} uid={uid} />;
  return <Area data={m.series} w={w} h={h} uid={uid} color={m.accent} />;
};

Object.assign(window, { SC, AR_MODULES, Tag, Delta, Area, Bars, Ring, Kpi, AIBlock, Rows, Pipeline, Funnel, ModuleChart });
