// app.jsx — Main shell + state for the Student Loan Strategy app.

const { useState: useStateApp, useMemo: useMemoApp, useEffect: useEffectApp } = React;
const LEng = window.LoanEngine;

const NAV = [
  { key: 'dashboard', label: 'Dashboard', icon: '◐' },
  { key: 'calculator', label: 'Calculator', icon: '◇' },
  { key: 'charts', label: 'Charts', icon: '◢' },
];

const CURRENT_YEAR = 2026;

const DEFAULTS = {
  planKey: 'plan5',
  balance: 48000,
  gradYear: 2024,
  salary: 45000,
  bonus: 0,
  salaryGrowth: 6,
  pension: 5,
  age: 24,
  monthlyOverpay: 250,
  lumpSum: 5000,
  lumpThenAction: 'invest',
  investReturn: 0.07,
  inflation: 0.025,
  investFee: 0.0025,
  wrapper: 'ISA'
};

// Years left until write-off, derived from graduation year + the plan's term.
function yearsRemainingFor(planKey, gradYear) {
  const plan = LEng.PLANS[planKey] || LEng.PLANS.plan5;
  const elapsed = Math.max(0, CURRENT_YEAR - gradYear);
  return Math.max(0, plan.writeOffYears - elapsed);
}

const TWEAK_DEFAULTS = /*EDITMODE-BEGIN*/{
  "theme": "dark",
  "fmtMode": "short",
  "chartStyle": "area",
  "preset": "moderate"
}/*EDITMODE-END*/;

function App() {
  const [t, setTweak] = useTweaks(TWEAK_DEFAULTS);
  const [screen, setScreen] = useStateApp('dashboard');
  const [inputs, setInputs] = useStateApp(DEFAULTS);

  // Apply theme + keep the shared global-nav in sync
  useEffectApp(() => {
    document.documentElement.setAttribute('data-theme', 'dark');
    const gnav = document.querySelector('global-nav');
    if (gnav) gnav.setAttribute('theme', 'dark');
  }, []);

  // Assumption presets
  useEffectApp(() => {
    if (t.preset === 'conservative') {
      setInputs((i) => ({ ...i, investReturn: 0.04, inflation: 0.03, salaryGrowth: 3 }));
    } else if (t.preset === 'moderate') {
      setInputs((i) => ({ ...i, investReturn: 0.07, inflation: 0.025, salaryGrowth: 6 }));
    } else if (t.preset === 'aggressive') {
      setInputs((i) => ({ ...i, investReturn: 0.10, inflation: 0.02, salaryGrowth: 9 }));
    }
  }, [t.preset]);

  // Run simulations (memoized)
  const results = useMemoApp(() => {
    const base = {
      planKey: inputs.planKey,
      balance: inputs.balance,
      yearsRemaining: yearsRemainingFor(inputs.planKey, inputs.gradYear),
      salary: inputs.salary + inputs.bonus,
      salaryGrowth: inputs.salaryGrowth / 100,
      monthlyOverpay: inputs.monthlyOverpay,
      lumpSum: inputs.lumpSum,
      lumpThenAction: inputs.lumpThenAction,
      investReturn: inputs.investReturn,
      inflation: inputs.inflation,
      investFee: inputs.investFee
    };
    return LEng.compareStrategies(base);
  }, [inputs]);

  const reco = useMemoApp(() => {
    return LEng.recommend(results, { monthlyOverpay: inputs.monthlyOverpay });
  }, [results, inputs.monthlyOverpay]);

  const plan = LEng.PLANS[inputs.planKey];
  const railMonthly = LEng.monthlyRepayment(plan, inputs.salary + inputs.bonus);

  function exportReport() {
    const std = results.standard, ovr = results.overpay, lump = results.lump, inv = results.invest;
    const netWorth = (s) => s.finalInvested - s.finalBalance;
    const payoff = (s) => s.payoffMonth == null
      ? `Written off (yr ${std.writeOffYears})`
      : (s.payoffMonth === 0 ? 'Cleared today' : `Year ${(s.payoffMonth / 12).toFixed(1)}`);
    const g = (n) => LEng.fmtGBP(n, 'full');
    window.PremiumReport.generate({
      tool: 'Student Loan Strategy',
      accent: '#5ec2a8',
      scenario: `${plan.label} · ${g(inputs.balance)} balance · ${g(inputs.salary)} salary · written off in year ${std.writeOffYears}`,
      verdict: reco ? { line: reco.headline, reasoning: reco.reasoning } : null,
      metrics: [
        { label: 'Monthly repayment', value: g(railMonthly) },
        { label: 'Interest (standard)', value: g(std.totalInterest) },
        { label: 'Written off', value: g(std.writtenOff) },
        { label: 'Interest saved by overpaying', value: g(std.totalInterest - ovr.totalInterest), accent: '#7b54c8' },
        { label: 'Investment pot instead', value: g(inv.finalInvested), accent: '#1f8a6d' },
        { label: 'Net advantage', value: (netWorth(inv) > netWorth(ovr) ? '+' : '') + g(netWorth(inv) - netWorth(ovr)) },
      ],
      chartTitle: 'Net wealth over time',
      chartSVG: window.PremiumReport.captureSVG('.main .card svg'),
      tables: [{
        title: 'Strategy comparison',
        headers: ['Strategy', 'Net wealth', 'Interest paid', 'Cleared by', 'Portfolio'],
        rows: [
          ['Standard', g(netWorth(std)), g(std.totalInterest), payoff(std), g(std.finalInvested)],
          ['Monthly overpay', g(netWorth(ovr)), g(ovr.totalInterest), payoff(ovr), g(ovr.finalInvested)],
          ['Lump sum', g(netWorth(lump)), g(lump.totalInterest), payoff(lump), g(lump.finalInvested)],
          ['Invest instead', g(netWorth(inv)), g(inv.totalInterest), payoff(inv), g(inv.finalInvested)],
        ],
        highlightRow: { standard: 0, overpay: 1, lump: 2, invest: 3 }[reco.best],
      }],
      notes: [
        reco.willRepay
          ? 'You\u2019re on track to clear this loan before write-off, so it behaves like real debt — every pound of interest you avoid is a genuine saving.'
          : 'You\u2019re unlikely to fully repay before write-off, so the loan behaves more like a graduate tax. Overpaying risks handing money to a balance that gets wiped anyway.',
        'A Stocks & Shares ISA shelters investment growth from tax, with a £20,000 annual allowance and full access to your money.',
        'Your repayment is a percentage of income above the threshold — not a function of the balance — so a higher salary, not a bigger balance, drives what you pay.',
      ],
    });
  }

  return (
    <React.Fragment>
      <div className="aurora"><div className="blob"></div></div>

      <div className="app" data-screen-label="Student Loan Strategy">
        <aside className="sidebar">
          <nav className="rail-nav">
            <div className="nav-group">
              <div className="nav-group-label">Strategy</div>
              {NAV.map((n) =>
              <button key={n.key}
              className={`nav-item ${screen === n.key ? 'active' : ''}`}
              onClick={() => setScreen(n.key)}>
                  <span className="ni-dot" />
                  <span className="ni-label">{n.label}</span>
                </button>
              )}
            </div>
            <div className="nav-group">
              <div className="nav-group-label">Scenario</div>
              <button className="nav-item" onClick={() => setInputs(DEFAULTS)}>
                <span className="ni-dot" />
                <span className="ni-label">Recent grad</span>
                <span className="ni-tag">Default</span>
              </button>
              <button className="nav-item" onClick={() => setInputs((i) => ({
                ...DEFAULTS, planKey: 'plan2', balance: 55000, salary: 85000,
                salaryGrowth: 8, monthlyOverpay: 500, age: 28, gradYear: 2020,
                lumpSum: 10000
              }))}>
                <span className="ni-dot" />
                <span className="ni-label">High earner</span>
              </button>
              <button className="nav-item" onClick={() => setInputs((i) => ({
                ...DEFAULTS, planKey: 'pgl', balance: 75000, salary: 60000,
                salaryGrowth: 5, monthlyOverpay: 300, age: 26, gradYear: 2023
              }))}>
                <span className="ni-dot" />
                <span className="ni-label">Postgrad</span>
              </button>
            </div>
          </nav>
          <div className="rail-foot">
            <div className="rail-foot-label">Current scenario</div>
            <div className="rail-foot-row"><span>{plan.label}</span><b>{LEng.fmtGBP(inputs.balance, t.fmtMode)}</b></div>
            <div className="rail-foot-row"><span>Salary · age</span><b>{LEng.fmtGBP(inputs.salary, t.fmtMode)} · {inputs.age}</b></div>
            <div className="rail-foot-row hero"><span>SL / month</span><b>{LEng.fmtGBP(railMonthly, t.fmtMode)}</b></div>
            <div className="rail-foot-note">Estimate only · not advice</div>
          </div>
        </aside>

        <main className="main">
          <div className="topbar">
            <div>
              <h1>
                {screen === 'dashboard' && <>Your loan is on <span className="accent">autopilot</span>.</>}
                {screen === 'calculator' && <>Student Loan Calculator</>}
                {screen === 'charts' && <>Charts</>}
              </h1>
              <div className="sub">
                {screen === 'dashboard' && 'Which strategy makes you wealthiest at write-off — recalculated as you tweak.'}
                {screen === 'calculator' && 'Real UK loan logic. Change anything; everything updates.'}
                {screen === 'charts' && 'Pictures of the same maths.'}
              </div>
            </div>
            <div className="topbar-actions">
              <button className="btn btn-ghost">Save scenario</button>
              <button className="btn btn-primary" onClick={exportReport}>↓ PDF report</button>
            </div>
          </div>

          {screen === 'dashboard' && <DashboardScreen inputs={inputs} results={results} reco={reco} fmtMode={t.fmtMode} chartStyle={t.chartStyle} />}
          {screen === 'calculator' && <CalculatorScreen inputs={inputs} setInputs={setInputs} results={results} fmtMode={t.fmtMode} chartStyle={t.chartStyle} />}
          {screen === 'charts' && <ChartsScreen inputs={inputs} results={results} fmtMode={t.fmtMode} chartStyle={t.chartStyle} />}
        </main>
      </div>

      <TweaksPanel>
        <TweakSection label="Display" />
        <TweakRadio label="Currency" value={t.fmtMode}
          options={[
            { value: 'short', label: '£48k' },
            { value: 'full', label: '£48,000' }
          ]}
          onChange={(v) => setTweak('fmtMode', v)} />
        <TweakRadio label="Chart style" value={t.chartStyle}
          options={[
            { value: 'line', label: 'Line' },
            { value: 'area', label: 'Area' }
          ]}
          onChange={(v) => setTweak('chartStyle', v)} />
        <TweakSection label="Assumptions" />
        <TweakRadio label="Preset" value={t.preset}
          options={[
            { value: 'conservative', label: 'Cautious' },
            { value: 'moderate', label: 'Middle' },
            { value: 'aggressive', label: 'Bold' }
          ]}
          onChange={(v) => setTweak('preset', v)} />
      </TweaksPanel>
    </React.Fragment>
  );
}

ReactDOM.createRoot(document.getElementById('root')).render(<App />);
