/* ===== NeuralField.jsx ===== */
/* global React */
// Astrid.global — full-page interactive neural field.
// Dense drifting nodes, distance-based links, and cursor interaction:
// the pointer repels nearby nodes and wires bright links to them.
function NeuralField() {
  const ref = React.useRef(null);
  React.useEffect(() => {
    const canvas = ref.current;
    if (!canvas) return;
    const ctx = canvas.getContext('2d');
    const reduce = window.matchMedia('(prefers-reduced-motion: reduce)').matches
      || new URLSearchParams(window.location.search).has('static');
    let raf, w, h, dpr, nodes = [];
    const mouse = { x: -9999, y: -9999, tx: -9999, ty: -9999, active: false };

    function resize() {
      dpr = Math.min(window.devicePixelRatio || 1, 2);
      w = window.innerWidth; h = window.innerHeight;
      canvas.width = w * dpr; canvas.height = h * dpr;
      canvas.style.width = w + 'px'; canvas.style.height = h + 'px';
      ctx.setTransform(dpr, 0, 0, dpr, 0, 0);
      const count = Math.min(170, Math.max(70, Math.round((w * h) / 11000)));
      nodes = Array.from({ length: count }, () => {
        const hub = Math.random() < 0.12;
        return {
          x: Math.random() * w, y: Math.random() * h,
          vx: (Math.random() - 0.5) * 0.28, vy: (Math.random() - 0.5) * 0.28,
          r: hub ? Math.random() * 1.6 + 1.8 : Math.random() * 1.3 + 0.5,
          hub, a: hub ? 0.9 : Math.random() * 0.4 + 0.3,
        };
      });
    }

    const LINK = 128, MOUSE_LINK = 190, REPEL = 150;

    function frame() {
      ctx.clearRect(0, 0, w, h);
      mouse.x += (mouse.tx - mouse.x) * 0.12;
      mouse.y += (mouse.ty - mouse.y) * 0.12;

      for (const n of nodes) {
        if (!reduce) { n.x += n.vx; n.y += n.vy; }
        // cursor repulsion
        if (mouse.active) {
          const dx = n.x - mouse.x, dy = n.y - mouse.y;
          const d = Math.hypot(dx, dy);
          if (d < REPEL && d > 0.01) {
            const f = (1 - d / REPEL) * 1.6;
            n.x += (dx / d) * f; n.y += (dy / d) * f;
          }
        }
        // wrap
        if (n.x < -20) n.x = w + 20; if (n.x > w + 20) n.x = -20;
        if (n.y < -20) n.y = h + 20; if (n.y > h + 20) n.y = -20;
      }

      // node-node links
      for (let i = 0; i < nodes.length; i++) {
        const a = nodes[i];
        for (let j = i + 1; j < nodes.length; j++) {
          const b = nodes[j];
          const dx = a.x - b.x, dy = a.y - b.y;
          const d = Math.hypot(dx, dy);
          if (d < LINK) {
            const o = (1 - d / LINK) * 0.28;
            ctx.strokeStyle = 'rgba(6,231,222,' + o + ')';
            ctx.lineWidth = 0.6;
            ctx.beginPath(); ctx.moveTo(a.x, a.y); ctx.lineTo(b.x, b.y); ctx.stroke();
          }
        }
      }

      // cursor links (brighter)
      if (mouse.active) {
        for (const n of nodes) {
          const dx = n.x - mouse.x, dy = n.y - mouse.y;
          const d = Math.hypot(dx, dy);
          if (d < MOUSE_LINK) {
            const o = (1 - d / MOUSE_LINK) * 0.6;
            ctx.strokeStyle = 'rgba(6,231,222,' + o + ')';
            ctx.lineWidth = 0.9;
            ctx.beginPath(); ctx.moveTo(mouse.x, mouse.y); ctx.lineTo(n.x, n.y); ctx.stroke();
          }
        }
        // cursor glow node
        ctx.fillStyle = 'rgba(6,231,222,0.9)';
        ctx.shadowColor = 'rgba(6,231,222,0.9)'; ctx.shadowBlur = 16;
        ctx.beginPath(); ctx.arc(mouse.x, mouse.y, 2.4, 0, Math.PI * 2); ctx.fill();
        ctx.shadowBlur = 0;
      }

      // nodes
      for (const n of nodes) {
        if (n.hub) { ctx.shadowColor = 'rgba(6,231,222,0.8)'; ctx.shadowBlur = 10; }
        ctx.fillStyle = 'rgba(' + (n.hub ? '120,255,247,' : '6,231,222,') + n.a + ')';
        ctx.beginPath(); ctx.arc(n.x, n.y, n.r, 0, Math.PI * 2); ctx.fill();
        ctx.shadowBlur = 0;
      }

      if (!reduce) raf = requestAnimationFrame(frame);
    }

    function onMove(e) { mouse.tx = e.clientX; mouse.ty = e.clientY; mouse.active = true; }
    function onLeave() { mouse.active = false; mouse.tx = -9999; mouse.ty = -9999; }
    function onTouch(e) { if (e.touches[0]) { mouse.tx = e.touches[0].clientX; mouse.ty = e.touches[0].clientY; mouse.active = true; } }

    resize();
    window.addEventListener('resize', resize);
    window.addEventListener('mousemove', onMove);
    window.addEventListener('mouseout', onLeave);
    window.addEventListener('touchmove', onTouch, { passive: true });
    window.addEventListener('touchend', onLeave);
    frame();
    return () => {
      cancelAnimationFrame(raf);
      window.removeEventListener('resize', resize);
      window.removeEventListener('mousemove', onMove);
      window.removeEventListener('mouseout', onLeave);
      window.removeEventListener('touchmove', onTouch);
      window.removeEventListener('touchend', onLeave);
    };
  }, []);

  return (
    <canvas ref={ref} aria-hidden="true" style={{
      position: 'fixed', inset: 0, zIndex: 0, pointerEvents: 'none',
    }} />
  );
}
window.NeuralField = NeuralField;


/* ===== Investors.jsx ===== */
/* global React */
// Astrid investors page — full regulatory content in the Arena theme.
function InvDocRow({ item }) {
  return (
    <a className="docRow" href={item.href} target="_blank" rel="noopener noreferrer">
      <span className="docT">{item.t}</span>
      <span className="docD">{item.d} <span className="docArrow">&#8599;</span></span>
    </a>
  );
}
function InvSection({ id, title, children }) {
  return (
    <section id={id} className="invSection" data-screen-label={title} data-reveal>
      <h2 className="invH2">{title}<span style={{ color: 'var(--astrid-teal)' }}>.</span></h2>
      {children}
    </section>
  );
}
function InvestorsPage() {
  const { Button } = window.AstridDesignSystem_4bd568;
  const D = window.ASTRID_INVESTOR_DATA || { rns: [], shareholderDocs: [], press: [] };
  const logoW = (window.__resources && window.__resources.logoWhite) || 'assets/astrid-wordmark-white.png';
  const FACTS = [['6,332,665,972', 'Shares in issue'], ['£0.001', 'Nominal value each'], ['76.64%', 'In public hands'], ['ASTR', 'AQSE ticker']];
  const IDS = [['LEI', '213800IXPX4Z2MKX2U28'], ['ISIN', 'GB00BK964W87'], ['SEDOL', 'BK964W8']];
  const QUICK = [['Board & Advisors', '#board'], ['Shareholders', '#shareholders'], ['Governance', '#governance'], ['Documents', '#documents'], ['RNS', '#rns'], ['Press', '#press'], ['Contacts', '#contacts']];
  const BOARD = [
    { name: 'Mark Creaser', role: 'Chair', bio: ["Mark Creaser is an operator and strategist with 20 years of experience leading teams and scaling high-trust businesses. An early adopter of Bittensor, Mark has become one of the network's clearest voices. As CEO of DSV Fund, the world's first liquid hedge fund exclusively dedicated to Bittensor, Mark designed the fund's growth engine and has been instrumental in securing structured OTC access to high-conviction subnets, building relationships across the network, and establishing DSV as a leading allocator inside Bittensor's rapidly expanding ecosystem. Mark is a thought leader developing a thesis-driven approach that frames TAO as the monetary layer for open intelligence rather than a speculative crypto trade."] },
    { name: 'Siam Kidd', role: 'Chief Executive Officer', bio: ["A former RAF pilot, Siam is a globally recognised crypto investor, trader, author of 2 books and thought leader with over 21 years of experience in financial markets, including M&A, and is the co-founder and CIO of DSV Fund, Bittensor's first liquid hedge fund. Siam brings a disciplined, data-driven approach to navigating volatile markets. He is one of the most knowledgeable and connected individuals within Bittensor and together with Mark, they have launched several AI start ups within Bittensor.", "As CEO, Siam will assume responsibility for leading Astrid's operating strategy, organisational development, and growth initiatives as the Company progresses its decentralised AI roadmap and expands its network participation."] },
    { name: 'Elliot Fielding', role: 'Chief Financial Officer', bio: ['Elliot Fielding qualified as a Chartered Accountant at Deloitte, with experience in Audit and Transaction Services. Elliot has advised clients ranging from large multinational and listed companies to smaller, privately owned and managed operations, in various sectors including law, TMT, real estate, sport and travel. Currently, he is the managing partner of Sampson Fielding, a firm of Chartered Accountants and Business Advisors. Elliot was previously a director of AQSE-listed Flex Labs Inc.'] },
    { name: 'Misha Sher', role: 'Non-Executive Director', bio: ["Misha is a senior marketing executive with over two decades of experience working with leading brands, rights holders and talent. Mr Sher spearheaded the growth of an award-winning sports, entertainment and culture business unit at MediaCom, one of the world's largest media and communications agencies. He has worked with some of the world's largest brands including eBay, Uber, Coca-Cola, P&G, American Airlines, Apple and Toyota on investment in leading cultural properties. He currently serves as NED at the European Sponsorship Association."] },
  ];
  const HOLDERS = [
    ['OAK Securities Ltd', '857,686,360', '13.55%'],
    ['Marallo Pte Ltd', '325,000,000', '5.14%'],
    ['Olivia Edwards', '296,500,000', '4.69%'],
    ['Siam Kidd', '190,560,368', '3.01%'],
    ['Mark Creaser', '166,666,666', '2.63%'],
  ];
  const CONTACTS = [
    { k: 'Registered Office', v: ['9th Floor', '16 Great Queen Street', 'London WC2B 5DG'] },
    { k: 'Registrars', v: ['Computershare Investor Services PLC', 'The Pavilions', 'Bridgwater Road', 'Bristol BS13 8AE'] },
    { k: 'Solicitors to the Company', v: ['Fladgate LLP', '9th Floor', '16 Great Queen Street', 'London WC2B 5DG'] },
    { k: 'Corporate Stockbrokers', v: ['Oak Securities', '90 Jermyn Street', 'London SW1Y 6JD'] },
    { k: 'AQSE Corporate Adviser', v: ['First Sentinel', '21 Arlington Street', 'London SW1A 1RN'] },
    { k: 'Auditors and Reporting Accountants', v: ['PKF Littlejohn LLP', '15 Westferry Circus', 'Canary Wharf', 'London E14 4HD'] },
  ];
  return (
    <React.Fragment>
      <nav className="cineNav" data-screen-label="Nav">
        <a href="./" style={{ display: 'flex', alignItems: 'center' }}>
          <img src={logoW} alt="Astrid" style={{ height: 22, width: 'auto' }} />
        </a>
        <div className="cineNavGroup">
          <a className="cineNavLink" href="https://taostats.io/subnets/127" target="_blank" rel="noopener noreferrer">Subnet 127</a>
          <Button variant="primary" size="sm" uppercase onClick={() => window.open('https://arena.astrid.global/', '_blank')}>Enter Arena</Button>
        </div>
      </nav>
      <main className="invMain" id="top">
        <header className="invHero" data-screen-label="Investors hero" data-reveal>
          <div className="invKicker"><span className="astrid-livedot" style={{ width: 6, height: 6 }} /> Aquis Stock Exchange &middot; Growth Market</div>
          <h1 className="invH1">Investors<span style={{ color: 'var(--astrid-teal)' }}>.</span></h1>
          <p className="invLede">Astrid is aiming to disintermediate the algo-trading/quant world. It's doing this by running recurring Trading Battles for AI Trading Agents to compete against each other for lucrative prize pools each week. Astrid gleans all the reasoning and execution intelligence from every trade these Agents place in order to perfect the in-house Trading Agent.</p>
          <p className="invBody">Astrid Intelligence PLC is incorporated under the laws of England and Wales under the Companies Act 2006 and the company number 11537452. The Company's shares are traded on the Growth Market of the Aquis Stock Exchange. The Company is headquartered in London, UK.</p>
          <div className="invFacts">
            {FACTS.map(([v, l]) => (
              <div className="invFact" key={l}>
                <div className="invFactV">{v}</div>
                <div className="invFactL">{l}</div>
              </div>
            ))}
          </div>
          <p className="invSmall">There are no restrictions on the transfer of ordinary shares in the Company. No securities are held in treasury. The Company is subject to the UK Takeover Code.</p>
          <div className="invIds">
            {IDS.map(([k, v]) => <span className="invId" key={k}><b>{k}</b>{v}</span>)}
          </div>
          <div className="quickRow">
            {QUICK.map(([l, h]) => <a className="quickPill" key={h} href={h}>{l}</a>)}
          </div>
        </header>

        <InvSection id="board" title="Board & Advisors">
          <div className="boardGrid">
            {BOARD.map((m) => (
              <article className="invCard boardCard" key={m.name}>
                <div className="boardRole">{m.role}</div>
                <h3 className="boardName">{m.name}</h3>
                {m.bio.map((p, i) => <p className="boardBio" key={i}>{p}</p>)}
              </article>
            ))}
          </div>
        </InvSection>

        <InvSection id="shareholders" title="Significant Shareholders">
          <div className="invCard holdTable">
            <div className="holdRow holdHead"><span>Holder</span><span>Ordinary shares</span><span>Holding</span></div>
            {HOLDERS.map(([n, s, p]) => (
              <div className="holdRow" key={n}><span>{n}</span><span>{s}</span><span className="holdPct">{p}</span></div>
            ))}
          </div>
        </InvSection>

        <InvSection id="governance" title="Corporate Governance">
          <p className="invBody">The Board of Directors are responsible for carrying out the Company's objectives, implementing its business strategy and the overall supervision of the Company's activities. The Board provides leadership within a framework of prudent and effective controls. The Board established the corporate governance framework of the Company and has overall responsibility for setting the Company's strategic aims, defining the business plan and strategy and managing the financial and operational resources of the Company.</p>
          <p className="invBody">The Board, which will meet not less than six times a year, will ensure that procedures, resources and controls are in place to ensure that AQSE Growth Market Access Rulebook compliance by the Company is operating effectively at all times and that the Directors are communicating effectively with the Company's AQSE Corporate Adviser regarding the Company's ongoing compliance with the AQSE Growth Market Access Rulebook and in relation to all announcements, notifications and potential transactions.</p>
        </InvSection>

        <InvSection id="documents" title="Shareholder Documents">
          <div className="docGrid">{D.shareholderDocs.map((it, i) => <InvDocRow item={it} key={i} />)}</div>
        </InvSection>

        <InvSection id="rns" title="RNS">
          <div className="docGrid">{D.rns.map((it, i) => <InvDocRow item={it} key={i} />)}</div>
          {D.rnsArchive && <a className="archiveLink" href={D.rnsArchive} target="_blank" rel="noopener noreferrer">Historical RNS archive (Cellular Goods) &#8599;</a>}
        </InvSection>

        <InvSection id="press" title="Press Releases">
          <div className="docGrid">{D.press.map((it, i) => <InvDocRow item={it} key={i} />)}</div>
        </InvSection>

        <InvSection id="contacts" title="Contacts">
          <div className="contactGrid">
            {CONTACTS.map((c) => (
              <div className="invCard contactCard" key={c.k}>
                <div className="contactK">{c.k}</div>
                <div className="contactV">{c.v.map((l, i) => <div key={i}>{l}</div>)}</div>
              </div>
            ))}
          </div>
        </InvSection>
      </main>
      <footer className="invFooter" data-screen-label="Footer">
        <img src={logoW} alt="Astrid" style={{ height: 18, width: 'auto' }} />
        <span className="invFootMid">&copy; Astrid Intelligence PLC &middot; 16 Great Queen Street, London WC2B 5DG</span>
        <div className="invFootLinks">
          <a href="./">Astrid.global</a>
          <a href="./updates.html">Updates</a>
          <a href="https://arena.astrid.global" target="_blank" rel="noopener noreferrer">Arena &#8599;</a>
          <a href="https://taostats.io/subnets/127" target="_blank" rel="noopener noreferrer">Subnet 127 &#8599;</a>
        </div>
      </footer>
    </React.Fragment>
  );
}
window.InvestorsPage = InvestorsPage;


function App(){return <React.Fragment><window.NeuralField /><window.InvestorsPage /></React.Fragment>;}
ReactDOM.createRoot(document.getElementById('root')).render(<App />);
const io=new IntersectionObserver(es=>{es.forEach(e=>{if(e.isIntersecting){e.target.classList.add('astrid-in');io.unobserve(e.target);}})},{threshold:0.08,rootMargin:'0px 0px -6% 0px'});
function scan(){document.querySelectorAll('[data-reveal]:not(.astrid-in)').forEach(el=>io.observe(el));}
setTimeout(scan,200);setTimeout(scan,800);window.addEventListener('load',scan);
