/* ============================================================
   Screens — Home, Category, Lesson intro, Runner, Complete.
   Each receives a `nav` object: { go(name, params), back(), home() }.
   ============================================================ */
(function () {
  const { useState, useMemo, useRef, useEffect } = React;
  const A = window.APP;

  function shuffle(a){ const x=a.slice(); for(let i=x.length-1;i>0;i--){ const j=(Math.random()*(i+1))|0; [x[i],x[j]]=[x[j],x[i]]; } return x; }
  // route a lesson to the right screen (alphabet + review have bespoke views)
  function openLesson(nav, id){
    if (id==='alphabet') return nav.go('alphabet', {});
    const f = A.findLesson(id);
    if (f && f.lesson.isReview) return nav.go('review', {});
    nav.go('lesson', { lessonId:id });
  }

  /* build an exercise queue for any lesson shape ------------------ */
  function buildQueue(lesson) {
    if (lesson.exercises) return lesson.exercises;
    const q = [];
    if (lesson.letters) {
      const pool = lesson.letters.filter(l => l.lat !== '—');
      const q = [];
      shuffle(pool).slice(0, 6).forEach(ans => {
        const distract = shuffle(pool.filter(l => l !== ans)).slice(0, 3);
        const options = shuffle([ans, ...distract]).map(l => l.ru);
        q.push({ kind:'choice', prompt:`Which letter makes the “${ans.snd}” sound?`,
          item:null, options, answer:ans.ru });
      });
      return q;
    } else if (lesson.teach) {
      lesson.teach.forEach(it => q.push({ kind:'learn', item:it }));
    } else {
      q.push({ kind:'learn', item:A.greetings.teach[0] });
    }
    return q;
  }
  function lessonItems(lesson){ return lesson.teach || lesson.letters || (lesson.exercises||[]).filter(e=>e.item).map(e=>e.item); }

  /* ============================================================ HOME */
  function Home({ nav }) {
    const L = A.learner;
    const T = id => A.findTrack(id);
    const cont = A.greetings;
    const path = [
      { id:'alphabet', label:'The Alphabet', track:T('foundations'), status:'done', sub:'33 letters' },
      { id:'greetings', label:'First Words', track:T('words'), status:'active', sub:'A1 · 8 phrases' },
      { id:'family', label:'Family & People', track:T('words'), status:'locked' },
      { id:'food', label:'Food & Drink', track:T('words'), status:'locked' },
    ];
    return (
      <div style={{ minHeight:'100%', background:'var(--bg)' }}>
        {/* header */}
        <div style={{ padding:'58px 20px 6px', display:'flex', alignItems:'center', justifyContent:'space-between' }}>
          <div>
            <div style={{ fontFamily:'"Golos Text",system-ui', fontWeight:600, fontSize:15, color:'var(--muted)' }}>Привет,</div>
            <div style={{ fontFamily:'"Bricolage Grotesque",system-ui', fontWeight:800, fontSize:27,
              color:'var(--ink)', letterSpacing:'-0.02em', lineHeight:1.05 }}>{L.name}</div>
          </div>
          <div style={{ display:'flex', alignItems:'center', gap:10 }}>
            <div style={{ display:'flex', alignItems:'center', gap:6, background:'var(--surface)',
              borderRadius:999, padding:'8px 13px', boxShadow:'0 1px 0 var(--line), 0 2px 8px -5px rgba(0,0,0,0.2)' }}>
              <Flame size={18} />
              <span style={{ fontFamily:'"Bricolage Grotesque",system-ui', fontWeight:800, fontSize:17, color:'var(--ink)' }}>{L.streak}</span>
            </div>
            <button onClick={() => nav.go('profile')} aria-label="Profile"
              style={{ appearance:'none', border:'none', cursor:'pointer', width:40, height:40, borderRadius:999,
                background:'var(--primary)', display:'flex', alignItems:'center', justifyContent:'center',
                boxShadow:'0 4px 12px -4px var(--primary)' }}>
              <span style={{ fontFamily:'"Bricolage Grotesque",system-ui', fontWeight:800, fontSize:18, color:'#fff' }}>{L.name[0]}</span>
            </button>
          </div>
        </div>

        {/* daily goal strip */}
        <div style={{ margin:'14px 20px 4px', display:'flex', alignItems:'center', gap:14,
          background:'var(--surface)', border:'1px solid var(--line)', borderRadius:18, padding:'13px 16px' }}>
          <Ring size={46} stroke={5} value={L.doneToday/L.dayGoalMin}>
            <span style={{ fontFamily:'"Bricolage Grotesque",system-ui', fontWeight:800, fontSize:13, color:'var(--ink)' }}>{L.doneToday}′</span>
          </Ring>
          <div style={{ flex:1 }}>
            <div style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:800, fontSize:15, color:'var(--ink)' }}>Daily goal</div>
            <div style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:600, fontSize:13, color:'var(--muted)' }}>
              {L.doneToday} of {L.dayGoalMin} min · {L.dayGoalMin-L.doneToday} to go
            </div>
          </div>
          <Badge color="var(--primary-deep)" bg="var(--primary-wash)">{L.level}</Badge>
        </div>

        {/* continue card */}
        <div style={{ padding:'18px 20px 6px' }}>
          <div style={{ fontFamily:'"JetBrains Mono",monospace', fontSize:11, fontWeight:600,
            letterSpacing:'0.14em', textTransform:'uppercase', color:'var(--muted)', padding:'0 2px 10px' }}>Continue</div>
          <button onClick={() => openLesson(nav, 'greetings')}
            style={{ appearance:'none', cursor:'pointer', width:'100%', textAlign:'left', border:'none',
              background:'var(--ink)', borderRadius:24, padding:'20px 20px 18px', color:'#fff',
              boxShadow:'0 18px 40px -20px rgba(40,20,10,0.7)', position:'relative', overflow:'hidden' }}>
            <div style={{ position:'absolute', right:-30, top:-30, width:140, height:140, borderRadius:999,
              background:T('words').color, opacity:0.5, filter:'blur(8px)' }}/>
            <div style={{ position:'relative' }}>
              <div style={{ display:'flex', alignItems:'center', gap:8, marginBottom:14 }}>
                <Badge color="#fff" bg="rgba(255,255,255,0.16)">Everyday Words · A1</Badge>
              </div>
              <div style={{ fontFamily:'"Bricolage Grotesque",system-ui', fontWeight:800, fontSize:26,
                letterSpacing:'-0.02em', lineHeight:1.05, marginBottom:6 }}>First Words</div>
              <div style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:600, fontSize:14,
                color:'rgba(255,255,255,0.7)', marginBottom:16 }}>{cont.blurb}</div>
              <div style={{ display:'flex', alignItems:'center', gap:12 }}>
                <div style={{ flex:1 }}><Bar value={0.25} color={T('words').color} /></div>
                <div style={{ display:'flex', alignItems:'center', gap:8, background:T('words').color,
                  color:'#fff', borderRadius:999, padding:'10px 16px',
                  fontFamily:'"Hanken Grotesk",system-ui', fontWeight:800, fontSize:14 }}>
                  Resume
                  <svg width="16" height="16" viewBox="0 0 24 24"><path d="M5 12h13M13 6l6 6-6 6" stroke="#fff" strokeWidth="2.4" fill="none" strokeLinecap="round" strokeLinejoin="round"/></svg>
                </div>
              </div>
            </div>
          </button>
        </div>

        {/* the path */}
        <div style={{ padding:'18px 20px 6px' }}>
          <div style={{ fontFamily:'"JetBrains Mono",monospace', fontSize:11, fontWeight:600,
            letterSpacing:'0.14em', textTransform:'uppercase', color:'var(--muted)', padding:'0 2px 12px' }}>Your path</div>
          <div style={{ position:'relative' }}>
            <div style={{ position:'absolute', left:26, top:18, bottom:18, width:2, background:'var(--line)' }}/>
            <div style={{ display:'flex', flexDirection:'column', gap:10 }}>
              {path.map(n => {
                const open = n.status !== 'locked';
                const isActive = n.status === 'active';
                return (
                  <button key={n.id} disabled={!open} onClick={() => open && openLesson(nav, n.id)}
                    style={{ appearance:'none', border:'none', cursor:open?'pointer':'default', textAlign:'left',
                      background: isActive?'var(--surface)':'transparent',
                      borderRadius:16, padding: isActive?'12px 14px':'8px 14px', display:'flex', alignItems:'center', gap:14,
                      boxShadow: isActive?'0 1px 0 var(--line), 0 8px 20px -14px rgba(0,0,0,0.3)':'none',
                      position:'relative', zIndex:1 }}>
                    <div style={{ position:'relative', zIndex:2 }}>
                      {n.status==='done'
                        ? <div style={{ width:30, height:30, borderRadius:999, background:n.track.color,
                            display:'flex', alignItems:'center', justifyContent:'center', boxShadow:'0 0 0 4px var(--bg)' }}>
                            <svg width="16" height="16" viewBox="0 0 24 24"><path d="M5 13l4 4 10-11" stroke="#fff" strokeWidth="2.6" fill="none" strokeLinecap="round" strokeLinejoin="round"/></svg>
                          </div>
                        : n.status==='active'
                        ? <div style={{ width:30, height:30, borderRadius:999, background:n.track.color,
                            boxShadow:`0 0 0 4px var(--bg), 0 0 0 6px ${n.track.color}`,
                            display:'flex', alignItems:'center', justifyContent:'center' }}>
                            <div style={{ width:10, height:10, borderRadius:999, background:'#fff' }}/>
                          </div>
                        : <div style={{ width:30, height:30, borderRadius:999, background:'var(--chip)',
                            boxShadow:'0 0 0 4px var(--bg)', display:'flex', alignItems:'center', justifyContent:'center' }}>
                            <svg width="13" height="13" viewBox="0 0 24 24"><path d="M6 11V8a6 6 0 0112 0v3" stroke="var(--muted)" strokeWidth="2" fill="none"/><rect x="4" y="11" width="16" height="9" rx="2.5" fill="var(--muted)"/></svg>
                          </div>}
                    </div>
                    <div style={{ flex:1 }}>
                      <div style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:800, fontSize:15.5,
                        color: open?'var(--ink)':'var(--muted)' }}>{n.label}</div>
                      {n.sub && <div style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:600, fontSize:12.5, color:'var(--muted)' }}>{n.sub}</div>}
                    </div>
                    {isActive && <span style={{ fontFamily:'"JetBrains Mono",monospace', fontSize:10, fontWeight:700,
                      color:n.track.color, letterSpacing:'0.08em' }}>NOW</span>}
                  </button>
                );
              })}
            </div>
          </div>
        </div>

        {/* categories preview + view all */}
        <div style={{ padding:'18px 20px 104px' }}>
          <div style={{ display:'flex', alignItems:'baseline', justifyContent:'space-between', padding:'0 2px 12px' }}>
            <span style={{ fontFamily:'"JetBrains Mono",monospace', fontSize:11, fontWeight:600,
              letterSpacing:'0.14em', textTransform:'uppercase', color:'var(--muted)' }}>Categories</span>
            <button onClick={() => nav.setTab('categories')}
              style={{ appearance:'none', border:'none', background:'transparent', cursor:'pointer',
                fontFamily:'"Hanken Grotesk",system-ui', fontSize:12.5, fontWeight:800, color:'var(--primary-deep)' }}>View all →</button>
          </div>
          <div style={{ display:'grid', gridTemplateColumns:'1fr 1fr', gap:12 }}>
            {A.tracks.slice(0, 4).map(t => (
              <TrackCard key={t.id} track={t} onClick={() => nav.go('category', { trackId:t.id })} />
            ))}
          </div>
        </div>
      </div>
    );
  }

  /* ======================================================== CATEGORY */
  function Category({ nav, trackId }) {
    const t = A.findTrack(trackId);
    const done = t.lessons.filter(l=>l.status==='done').length;
    const openable = l => l.isAlphabet || !!l.teach;
    return (
      <div style={{ minHeight:'100%', background:'var(--bg)' }}>
        <div style={{ padding:'50px 18px 0', display:'flex', alignItems:'center', justifyContent:'space-between', gap:12 }}>
          <div style={{ display:'flex', alignItems:'center', gap:10, minWidth:0 }}>
            <Emblem letter={t.emblem} color={t.color} size={34} radius={11} />
            <div style={{ fontFamily:'"Bricolage Grotesque",system-ui', fontWeight:800, fontSize:22,
              color:'var(--ink)', letterSpacing:'-0.02em', whiteSpace:'nowrap', overflow:'hidden', textOverflow:'ellipsis' }}>{t.name}</div>
          </div>
          <IconBtn kind="close" onClick={nav.back} />
        </div>
        <div style={{ padding:'14px 22px 6px' }}>
          <div style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:600, fontSize:14.5, color:'var(--muted)' }}>{t.subtitle}</div>
          <p style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:500, fontSize:14.5, color:'var(--ink)',
            opacity:0.8, lineHeight:1.5, marginTop:12, textWrap:'pretty' }}>{t.desc}</p>
          <div style={{ display:'flex', alignItems:'center', gap:12, marginTop:14 }}>
            <div style={{ flex:1 }}><Bar value={done/t.lessons.length} color={t.color} /></div>
            <span style={{ fontFamily:'"JetBrains Mono",monospace', fontWeight:600, fontSize:12, color:'var(--muted)' }}>{done}/{t.lessons.length}</span>
          </div>
        </div>

        <div style={{ padding:'16px 18px 30px', display:'flex', flexDirection:'column', gap:11 }}>
          {t.lessons.map((l, i) => {
            const status = l.status || (openable(l) ? 'open' : 'locked');
            const can = openable(l);
            return (
              <button key={l.id} disabled={!can} onClick={() => can && openLesson(nav, l.id)}
                style={{ appearance:'none', border:'1px solid var(--line)', cursor:can?'pointer':'default',
                  textAlign:'left', background:'var(--surface)', borderRadius:18, padding:'14px 15px',
                  display:'flex', alignItems:'center', gap:14, opacity: can?1:0.62 }}>
                <div style={{ width:40, height:40, borderRadius:12, flexShrink:0,
                  background: status==='locked'?'var(--chip)':t.tint,
                  display:'flex', alignItems:'center', justifyContent:'center' }}>
                  {status==='done'
                    ? <svg width="20" height="20" viewBox="0 0 24 24"><path d="M5 13l4 4 10-11" stroke={t.color} strokeWidth="2.6" fill="none" strokeLinecap="round" strokeLinejoin="round"/></svg>
                    : status==='locked'
                    ? <svg width="16" height="16" viewBox="0 0 24 24"><path d="M6 11V8a6 6 0 0112 0v3" stroke="var(--muted)" strokeWidth="2" fill="none"/><rect x="4" y="11" width="16" height="9" rx="2.5" fill="var(--muted)"/></svg>
                    : <span style={{ fontFamily:'"Bricolage Grotesque",system-ui', fontWeight:800, fontSize:16, color:t.color }}>{i+1}</span>}
                </div>
                <div style={{ flex:1 }}>
                  <div style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:800, fontSize:15.5,
                    color: status==='locked'?'var(--muted)':'var(--ink)' }}>{l.title}</div>
                  <div style={{ display:'flex', alignItems:'center', gap:8, marginTop:3 }}>
                    {l.cefr && l.cefr!=='—' && <Badge>{l.cefr}</Badge>}
                    {l.isReview && <Badge color="var(--primary-deep)" bg="var(--primary-wash)">SRS</Badge>}
                    <span style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:600, fontSize:12.5, color:'var(--muted)' }}>{l.minutes} min</span>
                  </div>
                </div>
                {can && <svg width="9" height="16" viewBox="0 0 9 16" style={{ flexShrink:0 }}><path d="M1 1l6 7-6 7" stroke="var(--muted)" strokeWidth="2" fill="none" strokeLinecap="round" strokeLinejoin="round"/></svg>}
              </button>
            );
          })}
        </div>
      </div>
    );
  }

  /* ============================================================ INTRO */
  function Intro({ nav, lessonId }) {
    const found = A.findLesson(lessonId);
    if (!found) return null;
    const { track, lesson } = found;
    if (lesson.isReview) { nav.go('review', {}); return null; }
    if (lesson.isAlphabet) { nav.go('alphabet', {}); return null; }
    const items = lessonItems(lesson);
    const preview = items.slice(0, 3);
    return (
      <div style={{ minHeight:'100%', background:'var(--bg)', display:'flex', flexDirection:'column' }}>
        <div style={{ padding:'56px 18px 0', display:'flex', alignItems:'center', gap:12 }}>
          <IconBtn kind="close" onClick={nav.back} />
        </div>
        <div style={{ flex:1, overflowY:'auto', padding:'10px 22px 20px' }}>
          <div style={{ display:'flex', alignItems:'center', gap:9, marginBottom:14 }}>
            <Emblem letter={track.emblem} color={track.color} size={30} radius={9} />
            <span style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:700, fontSize:13.5, color:track.color }}>{track.name}</span>
          </div>
          <div style={{ fontFamily:'"Bricolage Grotesque",system-ui', fontWeight:800, fontSize:32,
            color:'var(--ink)', letterSpacing:'-0.02em', lineHeight:1.04 }}>{lesson.title}</div>
          <div style={{ display:'flex', alignItems:'center', gap:9, marginTop:12 }}>
            {lesson.cefr && lesson.cefr!=='—' && <Badge>{lesson.cefr}</Badge>}
            <span style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:600, fontSize:13.5, color:'var(--muted)' }}>
              {lesson.minutes} min · {items.length} {items[0] && items[0].type==='letter'?'letters':'items'}
            </span>
          </div>
          {lesson.blurb && <p style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:500, fontSize:15,
            color:'var(--ink)', opacity:0.82, lineHeight:1.5, marginTop:14, textWrap:'pretty' }}>{lesson.blurb}</p>}

          <div style={{ fontFamily:'"JetBrains Mono",monospace', fontSize:11, fontWeight:600,
            letterSpacing:'0.14em', textTransform:'uppercase', color:'var(--muted)', padding:'24px 2px 12px' }}>You’ll learn</div>
          <div style={{ display:'flex', flexDirection:'column', gap:12 }}>
            {preview.map((it, i) => <StackedGloss key={i} item={it} compact />)}
          </div>
          {items.length > preview.length &&
            <div style={{ textAlign:'center', fontFamily:'"Hanken Grotesk",system-ui', fontWeight:700,
              fontSize:13.5, color:'var(--muted)', paddingTop:14 }}>+{items.length-preview.length} more inside</div>}
        </div>
        <div style={{ padding:'12px 20px calc(16px + env(safe-area-inset-bottom))', borderTop:'1px solid var(--line)',
          background:'var(--bg)' }}>
          <Btn full onClick={() => nav.go('runner', { lessonId })}>Start lesson</Btn>
        </div>
      </div>
    );
  }

  /* =========================================================== RUNNER */
  function Runner({ nav, lessonId }) {
    const found = A.findLesson(lessonId);
    const { track, lesson } = found;
    const queue = useMemo(() => buildQueue(lesson), [lessonId]);
    const [idx, setIdx] = useState(0);
    const [correct, setCorrect] = useState(0);
    const [graded, setGraded] = useState(0);
    const ex = queue[idx];

    const advance = (wasCorrect) => {
      let nc = correct, ng = graded;
      if (ex.kind !== 'learn') { ng = graded + 1; setGraded(ng); if (wasCorrect) { nc = correct + 1; setCorrect(nc); } }
      if (idx + 1 >= queue.length) {
        const acc = ng>0 ? Math.round(nc/ng*100) : 100;
        nav.go('complete', { lessonId, accuracy:acc, learned:lessonItems(lesson).length });
      } else setIdx(idx + 1);
    };

    const body = (() => {
      switch (ex.kind) {
        case 'learn':  return <LearnCard item={ex.item} onNext={() => advance(true)} />;
        case 'choice': return <ChoiceExercise ex={ex} onNext={advance} />;
        case 'listen': return <ListenExercise ex={ex} onNext={advance} />;
        case 'match':  return <MatchExercise ex={ex} onNext={advance} />;
        case 'speak':  return <SpeakExercise ex={ex} onNext={advance} />;
        default: return null;
      }
    })();

    return (
      <div style={{ height:'100%', display:'flex', flexDirection:'column', background:'var(--bg)' }}>
        <div style={{ display:'flex', alignItems:'center', gap:13, padding:'52px 18px 12px' }}>
          <IconBtn kind="close" onClick={nav.home} />
          <div style={{ flex:1 }}><Bar value={(idx)/queue.length} color={track.color} /></div>
          <span style={{ fontFamily:'"JetBrains Mono",monospace', fontWeight:600, fontSize:13, color:'var(--muted)' }}>{idx+1}/{queue.length}</span>
        </div>
        <div style={{ flex:1, minHeight:0, position:'relative' }}>
          {React.cloneElement(body, { key:idx })}
        </div>
      </div>
    );
  }

  /* ========================================================= COMPLETE */
  function Complete({ nav, lessonId, accuracy, learned }) {
    const found = A.findLesson(lessonId);
    const { track, lesson } = found;
    const awarded = (lesson && lesson.minutes) || 5; // real minutes for this lesson (doc 04 §5.2)
    const [hint, setHint] = useState(false);

    // 2026-06-05 7:25PM — persist completion when signed in (doc 04 §5.2). PENDING USER TESTING
    useEffect(() => {
      let live = true;
      (async () => {
        try {
          if (!window.sb) return;
          const { data } = await window.sb.auth.getUser();
          const id = data && data.user ? data.user.id : null;
          if (!id) { if (live) { setHint(true); try { localStorage.setItem('ru_lesson_' + lessonId, JSON.stringify({ accuracy, at: Date.now() })); } catch (e) {} } return; }

          // 1) lesson progress row
          const up = await window.sb.from('user_progress').upsert(
            { user_id: id, item_type: 'lesson', item_key: lessonId, status: 'done', accuracy: (typeof accuracy === 'number' ? accuracy : null), completed_at: new Date().toISOString() },
            { onConflict: 'user_id,item_type,item_key' }
          );
          if (up.error) console.error('[auth:complete] lesson upsert', up.error.message);

          // 2) today's streak row — accumulate minutes, recompute goal_met
          const d = new Date();
          const today = `${d.getFullYear()}-${String(d.getMonth()+1).padStart(2,'0')}-${String(d.getDate()).padStart(2,'0')}`;
          const [{ data: existing }, { data: settings }] = await Promise.all([
            window.sb.from('user_streaks').select('minutes').eq('user_id', id).eq('activity_date', today).maybeSingle(),
            window.sb.from('user_settings').select('daily_goal_minutes').eq('user_id', id).maybeSingle(),
          ]);
          const goal = (settings && settings.daily_goal_minutes) || 10;
          const newMins = ((existing && existing.minutes) || 0) + awarded;
          const st = await window.sb.from('user_streaks').upsert(
            { user_id: id, activity_date: today, minutes: newMins, goal_met: newMins >= goal },
            { onConflict: 'user_id,activity_date' }
          );
          if (st.error) console.error('[auth:complete] streak upsert', st.error.message);

          // reflect new minutes in the dashboard ring/streak on return
          if (nav.rehydrate) await nav.rehydrate();
        } catch (e) { console.error('[auth:complete] persist error', e); }
      })();
      return () => { live = false; };
    }, []);

    return (
      <div style={{ height:'100%', display:'flex', flexDirection:'column', background:'var(--bg)' }}>
        <div style={{ flex:1, overflowY:'auto', padding:'70px 24px 20px', display:'flex',
          flexDirection:'column', alignItems:'center', textAlign:'center' }}>
          <div style={{ animation:'pop .5s cubic-bezier(.2,1.4,.4,1)' }}><Mascot size={92} /></div>
          <div style={{ fontFamily:'"JetBrains Mono",monospace', fontSize:11, fontWeight:600,
            letterSpacing:'0.16em', textTransform:'uppercase', color:track.color, marginTop:18 }}>Lesson complete</div>
          <div style={{ fontFamily:'"Bricolage Grotesque",system-ui', fontWeight:800, fontSize:30,
            color:'var(--ink)', letterSpacing:'-0.02em', marginTop:6 }}>Молодец!</div>
          <div style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:600, fontSize:14.5,
            color:'var(--muted)', marginTop:4 }}>“Well done” — you finished {lesson.title}.</div>

          <div style={{ display:'flex', gap:11, marginTop:26, width:'100%' }}>
            {[
              { v:`${learned}`, l:'Items learned', c:track.color },
              { v:`${accuracy}%`, l:'Accuracy', c:'oklch(0.60 0.13 150)' },
              { v:`+${awarded}`, l:'Day streak min', c:'var(--primary)' },
            ].map((s,i) => (
              <div key={i} style={{ flex:1, background:'var(--surface)', border:'1px solid var(--line)',
                borderRadius:18, padding:'15px 8px' }}>
                <div style={{ fontFamily:'"Bricolage Grotesque",system-ui', fontWeight:800, fontSize:24, color:s.c }}>{s.v}</div>
                <div style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:600, fontSize:11.5, color:'var(--muted)', marginTop:2 }}>{s.l}</div>
              </div>
            ))}
          </div>

          <div style={{ marginTop:22, width:'100%', background:'var(--primary-wash)', borderRadius:18,
            padding:'15px 16px', display:'flex', alignItems:'center', gap:12, textAlign:'left' }}>
            <Flame size={22} />
            <div style={{ flex:1 }}>
              <div style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:800, fontSize:14.5, color:'var(--ink)' }}>These words are now in review</div>
              <div style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:600, fontSize:12.5, color:'var(--primary-deep)' }}>We’ll resurface them right before you forget.</div>
            </div>
          </div>
        </div>
        <div style={{ padding:'12px 20px calc(16px + env(safe-area-inset-bottom))', borderTop:'1px solid var(--line)',
          display:'flex', flexDirection:'column', gap:10 }}>
          {hint && (
            <div style={{ display:'flex', alignItems:'center', gap:10, background:'var(--primary-wash)',
              borderRadius:14, padding:'10px 12px' }}>
              <span style={{ flex:1, fontFamily:'"Hanken Grotesk",system-ui', fontWeight:700, fontSize:12.5, color:'var(--primary-deep)' }}>
                Sign in to save your progress
              </span>
              <button onClick={() => nav.go('auth')} style={{ appearance:'none', border:'none', cursor:'pointer',
                background:'var(--primary)', color:'#fff', borderRadius:999, padding:'6px 12px',
                fontFamily:'"Hanken Grotesk",system-ui', fontWeight:800, fontSize:12 }}>Sign in</button>
              <button onClick={() => setHint(false)} aria-label="Dismiss" style={{ appearance:'none', border:'none',
                cursor:'pointer', background:'transparent', color:'var(--muted)', padding:'4px', display:'flex' }}>
                <svg width="16" height="16" viewBox="0 0 24 24"><path d="M6 6l12 12M18 6L6 18" stroke="currentColor" strokeWidth="2.2" fill="none" strokeLinecap="round"/></svg>
              </button>
            </div>
          )}
          <Btn full onClick={() => nav.go('review', {})}>Review these words</Btn>
          <Btn variant="ghost" full onClick={nav.home}>Back to home</Btn>
        </div>
      </div>
    );
  }

  /* ======================================================= REVIEW WRAP */
  function Review({ nav }) {
    const [done, setDone] = useState(null);
    if (done) {
      return (
        <div style={{ height:'100%', display:'flex', flexDirection:'column', background:'var(--bg)' }}>
          <div style={{ flex:1, display:'flex', flexDirection:'column', alignItems:'center', justifyContent:'center',
            textAlign:'center', padding:24 }}>
            <Mascot size={84} />
            <div style={{ fontFamily:'"Bricolage Grotesque",system-ui', fontWeight:800, fontSize:26,
              color:'var(--ink)', marginTop:16 }}>Review done</div>
            <div style={{ fontFamily:'"Hanken Grotesk",system-ui', fontWeight:600, fontSize:14, color:'var(--muted)', marginTop:6 }}>
              {done.easy} easy · {done.good} good · {done.again} to repeat
            </div>
          </div>
          <div style={{ padding:'12px 20px calc(16px + env(safe-area-inset-bottom))' }}>
            <Btn full onClick={nav.home}>Done</Btn>
          </div>
        </div>
      );
    }
    return <FlashcardDeck deck={A.reviewDeck} onExit={nav.home} onFinish={setDone} />;
  }

  Object.assign(window, { Home, Category, Intro, Runner, Complete, Review });
})();
