// Fill by Flow — screens
// Listen, SingleFluid, JobTable, Capacity, Safety

const { useState: useSt, useEffect: useEf, useRef: useRf } = React;

// Confidence can arrive as number (0-1, demo) or string ("oem"/"verified"/"estimated", live).
// Returns display label or '' — never "NaN%".
function formatConfidenceLabel(c) {
  if (c == null) return '';
  if (typeof c === 'number' && Number.isFinite(c)) {
    return `${(c * 100).toFixed(0)}% CONFIDENCE`;
  }
  if (typeof c === 'string') {
    const s = c.trim();
    if (!s) return '';
    return `${s.toUpperCase()} CONFIDENCE`;
  }
  return '';
}

const QUART_TO_LITER = 0.946;

function capacityToQuarts(capacity, capacityUnits) {
  if (capacity == null || !Number.isFinite(Number(capacity))) return null;
  const u = String(capacityUnits || '').trim().toUpperCase();
  if (['QT', 'QTS', 'QUART', 'QUARTS'].includes(u)) return Number(capacity);
  if (['GAL', 'GALS', 'GALLON', 'GALLONS'].includes(u)) return Number(capacity) * 4;
  if (['L', 'LT', 'LITER', 'LITERS', 'LITRE', 'LITRES'].includes(u)) return Number(capacity) / QUART_TO_LITER;
  return null;
}

function sumCapacitiesInQuarts(items) {
  let total = 0;
  for (const item of items) {
    const quarts = capacityToQuarts(item.capacity, item.units);
    if (quarts == null) return null;
    total += quarts;
  }
  return total;
}

// ══ LISTEN SCREEN ═════════════════════════════════════
function ListenScreen({ state, onDemo, onToggle, connStatus }) {
  const { listening, transcript } = state;
  const requestingPermission = connStatus === 'requesting_permission';
  const connecting = connStatus === 'connecting';
  const resolving = connStatus === 'resolving';
  const error = connStatus === 'error';
  const micActive = listening || requestingPermission || connecting || resolving;
  const voiceLinkLabel = listening
    ? 'LIVE'
    : resolving
      ? 'WORKING'
      : error
        ? 'ERROR'
        : requestingPermission || connecting
          ? 'CONNECTING'
          : 'READY';
  const micLabel = listening
    ? 'LISTENING...'
    : requestingPermission
      ? 'ENABLE MICROPHONE'
      : connecting
        ? 'CONNECTING...'
        : resolving
          ? 'WORKING...'
          : error
            ? 'TAP TO RETRY'
            : 'TAP TO SPEAK';
  return (
    <div style={{...screenStyle, paddingTop:54, display:'flex', flexDirection:'column', justifyContent:'space-between'}}>
      <div style={{
        flex:1, display:'flex', flexDirection:'column', alignItems:'center', justifyContent:'center',
        gap:22, padding:'18px 16px'
      }}>
        <div style={diagBlock}>
          <DiagRow k="Voice Link" v={<><span style={{
            display:'inline-block', width:7, height:7, borderRadius:'50%',
            marginRight:6, verticalAlign:'middle',
            background: listening ? 'var(--accent)' : error ? 'var(--red)' : 'var(--amber)',
            boxShadow: listening ? '0 0 6px var(--acc-glow)' : error ? '0 0 6px rgba(255,51,51,0.3)' : '0 0 6px rgba(245,166,35,0.3)'
          }} />{voiceLinkLabel}</>} />
          <DiagRow k="Fluid DB" v="142,881 SPECS" />
          <DiagRow k="Mode" v="SINGLE · JOB · CAPACITY" />
          <div style={{
            padding:'14px 14px 16px',
            fontFamily:"'DM Mono',monospace",
            fontSize: listening ? 17 : 16,
            color: listening ? 'var(--text)' : 'var(--dim)',
            lineHeight:1.5, letterSpacing:'0.02em',
            minHeight:58
          }}>
            {transcript || "Say a fluid, a job, or 'how much'"}
          </div>
        </div>

        <Waveform active={listening} />
      </div>

      <div style={{padding:'0 16px 6px'}}>
        <MicSlab listening={micActive} label={micLabel} onTap={onToggle} />
        <div style={{
          fontFamily:"'DM Mono',monospace", fontSize:12,
          letterSpacing:'0.2em', textTransform:'uppercase',
          color:'var(--muted)', textAlign:'center', marginTop:10
        }}>Year · Make · Model · Fluid or Job</div>
      </div>

      <div style={{
        width:'100%', borderTop:'2px solid var(--border)',
        padding:'12px 16px calc(14px + env(safe-area-inset-bottom))',
        background:'var(--panel)', flexShrink:0
      }}>
        <div style={{
          fontFamily:"'DM Mono',monospace", fontSize:11,
          letterSpacing:'0.2em', textTransform:'uppercase',
          color:'var(--dim)', marginBottom:9
        }}>— Tap to demo —</div>
        <div style={{display:'flex', gap:8}}>
          <DemoBtn onClick={() => onDemo('single')} html='"19 F-150<br/>oil change"' />
          <DemoBtn onClick={() => onDemo('job')} html='"19 F-150<br/>full service"' />
          <DemoBtn onClick={() => onDemo('capacity')} html='"how much<br/>oil"' />
        </div>
        <div style={{textAlign:'center', marginTop:12}}>
          <OlpCredit />
        </div>
      </div>
    </div>
  );
}

function DemoBtn({ onClick, html }) {
  return (
    <button onClick={onClick} style={{
      flex:1, background:'var(--panel-2)',
      border:'2px solid var(--border-h)', color:'var(--text-d)',
      fontFamily:"'DM Mono',monospace", fontSize:12,
      letterSpacing:'0.03em', padding:'11px 6px',
      cursor:'pointer', lineHeight:1.55, textAlign:'center'
    }}
    onMouseDown={(e)=>{e.currentTarget.style.borderColor='var(--accent)'; e.currentTarget.style.color='var(--accent)';}}
    onMouseUp={(e)=>{e.currentTarget.style.borderColor='var(--border-h)'; e.currentTarget.style.color='var(--text-d)';}}
    dangerouslySetInnerHTML={{__html: html}}
    />
  );
}

// ══ SINGLE FLUID SCREEN ═══════════════════════════════
function SingleFluidScreen({ data, veh, onBack, onWrong, density, units }) {
  const [wetDry, setWetDry] = useSt("refill"); // refill | wet | dry
  const [showMatrix, setShowMatrix] = useSt(false);
  const [pouring, setPouring] = useSt(false);
  const [poured, setPoured] = useSt(0);
  const [wrongState, setWrongState] = useSt('idle'); // idle | sending | done | error

  const capDisplay = units === 'metric'
    ? data.capacity.metric.toFixed(2)
    : data.capacity[wetDry === 'dry' ? 'dry' : 'wet'].toFixed(1);
  const capUnits = units === 'metric' ? 'L' : data.capacity.units;

  // Simulated pour progress
  useEf(() => {
    if (!pouring) return;
    const start = Date.now();
    const target = parseFloat(capDisplay);
    const dur = 4000;
    const tick = setInterval(() => {
      const e = Math.min(1, (Date.now() - start) / dur);
      setPoured(target * e);
      if (e >= 1) { clearInterval(tick); setPouring(false); }
    }, 60);
    return () => clearInterval(tick);
  }, [pouring, capDisplay]);

  const pourPct = (poured / parseFloat(capDisplay)) * 100;

  return (
    <div style={{...screenStyle, paddingTop:54}}>
      {/* veh bar */}
      <div style={{background:'var(--panel)', borderBottom:'2px solid var(--border)', padding:'11px 16px', flexShrink:0}}>
        <div style={microLabel}>Vehicle · Fluid</div>
        <div style={{fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:19, textTransform:'uppercase', letterSpacing:'0.06em', color:'var(--text)', lineHeight:1.1}}>
          {veh.year} {veh.make} {veh.model}
        </div>
        <div style={{fontFamily:"'Barlow Condensed',sans-serif", fontWeight:700, fontSize:14, textTransform:'uppercase', letterSpacing:'0.08em', color:'var(--mid)', marginTop:1}}>
          {veh.engine}
        </div>
      </div>

      {/* main zone */}
      <div style={{flex:1, overflowY:'auto', position:'relative'}}>
        <div style={{padding:'14px 16px 0', position:'relative'}}>
          <SideRail />

          {/* fluid name header */}
          <div style={{display:'flex', justifyContent:'space-between', alignItems:'flex-end', paddingLeft:10}}>
            <div>
              <div style={{fontFamily:"'DM Mono',monospace", fontSize:9, letterSpacing:'0.22em', textTransform:'uppercase', color:'var(--muted)'}}>
                {data.category}
              </div>
              <div style={{fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:30, textTransform:'uppercase', letterSpacing:'0.04em', color:'var(--text)', lineHeight:1, marginTop:3}}>
                {data.component}
              </div>
            </div>
            <button onClick={() => setWetDry(wetDry === 'refill' ? 'dry' : 'refill')} style={{
              background:'var(--panel-2)', border:'2px solid var(--border-h)',
              padding:'6px 10px', cursor:'pointer',
              fontFamily:"'DM Mono',monospace", fontSize:9,
              letterSpacing:'0.14em', textTransform:'uppercase',
              color: wetDry === 'refill' ? 'var(--accent)' : 'var(--amber)'
            }}>
              {wetDry === 'refill' ? 'REFILL (FILTER)' : 'DRY FILL'}
            </button>
          </div>

          {/* BIG CAPACITY NUMBER + METER */}
          <div style={{display:'flex', alignItems:'flex-end', gap:18, marginTop:22, paddingLeft:10}}>
            <div style={{flex:1}}>
              <div style={{
                fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900,
                fontSize:'clamp(120px, 34vw, 170px)',
                lineHeight:0.82, color:'var(--accent)',
                letterSpacing:'-0.02em',
                textShadow:'0 0 56px var(--acc-glow)'
              }}>{capDisplay}</div>
              <div style={{display:'flex', alignItems:'center', gap:10, marginTop:10}}>
                <span style={{
                  fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:30,
                  color:'var(--text-d)', textTransform:'uppercase', letterSpacing:'0.06em',
                  border:'2px solid var(--border-h)', padding:'5px 12px', lineHeight:1
                }}>{capUnits}</span>
                <span style={{fontFamily:"'DM Mono',monospace", fontSize:11, color:'var(--muted)', letterSpacing:'0.1em'}}>
                  {units === 'metric' ? `${data.capacity[wetDry==='dry'?'dry':'wet']} QT` : `${data.capacity.metric.toFixed(2)} L`}
                </span>
              </div>
            </div>
            {/* FLUID METER */}
            {density !== "industrial" && (
              <div style={{paddingBottom:4}}>
                <FluidMeter
                  value={pouring || poured > 0 ? poured : parseFloat(capDisplay)}
                  max={parseFloat(capDisplay)}
                  label={pouring ? "POURING" : poured > 0 ? "POURED" : "TARGET"}
                  density={density}
                />
              </div>
            )}
          </div>

          {/* SPEC BLOCK — novel decoder */}
          <div style={{
            marginTop:20, padding:'14px 14px',
            background:'var(--panel)',
            border:'2px solid var(--border-h)',
            borderLeft:'4px solid var(--accent)'
          }}>
            <div style={{display:'flex', justifyContent:'space-between', alignItems:'flex-start', gap:10}}>
              <div style={{flex:1}}>
                <div style={microLabel}>Spec · Grade</div>
                <div style={{
                  fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:38,
                  color:'var(--accent)', letterSpacing:'0.04em', lineHeight:1, marginTop:4
                }}>{data.spec.grade}</div>
                <div style={{fontFamily:"'DM Mono',monospace", fontSize:10, color:'var(--text-d)', letterSpacing:'0.08em', marginTop:6, lineHeight:1.5}}>
                  {data.spec.standard}
                </div>
                <div style={{fontFamily:"'DM Mono',monospace", fontSize:9, color:'var(--muted)', letterSpacing:'0.1em', marginTop:3}}>
                  OEM: {data.spec.oem}
                </div>
              </div>
              <button onClick={() => setShowMatrix(!showMatrix)} style={{
                background:'none', border:'1px solid var(--border-h)',
                color:'var(--accent)', padding:'6px 10px', cursor:'pointer',
                fontFamily:"'DM Mono',monospace", fontSize:9,
                letterSpacing:'0.14em', textTransform:'uppercase'
              }}>
                {showMatrix ? 'HIDE MIX' : 'MIX CHK'}
              </button>
            </div>

            {showMatrix && (
              <div style={{marginTop:12, borderTop:'1px solid var(--border)', paddingTop:10}}>
                <div style={{...microLabel, color:'var(--accent)'}}>✓ COMPATIBLE</div>
                {data.compatible.map((c, i) => (
                  <div key={i} style={{fontFamily:"'DM Mono',monospace", fontSize:10, color:'var(--text-d)', letterSpacing:'0.04em', padding:'3px 0'}}>
                    <span style={{color:'var(--accent)', marginRight:6}}>✓</span>{c}
                  </div>
                ))}
                <div style={{...microLabel, color:'var(--red)', marginTop:10}}>✗ NEVER USE</div>
                {data.incompatible.map((c, i) => (
                  <div key={i} style={{fontFamily:"'DM Mono',monospace", fontSize:10, color:'var(--text-d)', letterSpacing:'0.04em', padding:'3px 0'}}>
                    <span style={{color:'var(--red)', marginRight:6}}>✗</span>{c}
                  </div>
                ))}
              </div>
            )}
          </div>

          {/* PROCEDURE — numbered */}
          <div style={{marginTop:14}}>
            <div style={{...microLabel, paddingLeft:4, marginBottom:8}}>Procedure · voice "next" to advance</div>
            {data.procedure.map((p, i) => (
              <div key={i} style={{
                display:'grid', gridTemplateColumns:'36px 1fr',
                borderTop: i === 0 ? '1px solid var(--border)' : 'none',
                borderBottom:'1px solid var(--border)'
              }}>
                <div style={{
                  display:'flex', alignItems:'center', justifyContent:'center',
                  borderRight:'1px solid var(--border)',
                  fontFamily:"'DM Mono',monospace", fontSize:12,
                  color:'var(--muted)', letterSpacing:'0.1em'
                }}>
                  0{i+1}
                </div>
                <div style={{padding:'10px 12px'}}>
                  <div style={{fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:15, color:'var(--text)', textTransform:'uppercase', letterSpacing:'0.06em'}}>
                    {p.step}
                  </div>
                  <div style={{fontFamily:"'DM Mono',monospace", fontSize:9, color:'var(--muted)', letterSpacing:'0.04em', lineHeight:1.5, marginTop:2}}>
                    {p.detail}
                  </div>
                </div>
              </div>
            ))}
          </div>

          {/* FLAGS */}
          <div style={{display:'flex', gap:6, flexWrap:'wrap', marginTop:14, paddingLeft:4}}>
            <Flag kind="green">SYNTHETIC</Flag>
            <Flag kind="green">OEM SPEC</Flag>
            <Flag kind="amber">TURBO</Flag>
            <Flag kind="blue">{data.interval.miles/1000}K MI · {data.interval.months}MO</Flag>
          </div>

          {/* source */}
          <div style={{
            margin:'14px 0 14px', padding:'10px 14px',
            background:'var(--panel)', border:'2px solid var(--border-h)',
            borderLeft:'4px solid var(--accent)'
          }}>
            <div style={{...microLabel}}>Source{formatConfidenceLabel(data.confidence) ? ` · ${formatConfidenceLabel(data.confidence)}` : ''}</div>
            <div style={{fontFamily:"'DM Mono',monospace", fontSize:10, color:'var(--text-d)', letterSpacing:'0.08em', lineHeight:1.5, marginTop:2}}>
              {data.source}
            </div>
          </div>

          <div style={{display:'flex', alignItems:'center', gap:8, paddingLeft:4, paddingBottom:10, fontFamily:"'DM Mono',monospace", fontSize:8, letterSpacing:'0.16em', textTransform:'uppercase', color:'var(--dim)'}}>
            <div style={{width:5, height:5, borderRadius:'50%', background:'var(--accent)', animation:'fbf-adot 2.5s ease-in-out infinite'}} />
            Screen stays on · voice "new query" to reset
          </div>
        </div>
      </div>

      {/* POUR + action bar */}
      <div style={{flexShrink:0, padding:'10px 16px 14px', borderTop:'2px solid var(--border)', background:'var(--panel)', display:'flex', flexDirection:'column', gap:8}}>
        <button onClick={() => { setPoured(0); setPouring(true); }} style={{
          width:'100%', height:48,
          background: pouring ? 'var(--panel-2)' : 'transparent',
          border: pouring ? '2px solid var(--accent)' : '2px solid var(--border-h)',
          color: pouring ? 'var(--accent)' : 'var(--text-d)',
          fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:15,
          letterSpacing:'0.14em', textTransform:'uppercase', cursor:'pointer',
          position:'relative', overflow:'hidden'
        }}>
          <div style={{
            position:'absolute', left:0, top:0, bottom:0,
            width: pouring ? `${pourPct}%` : (poured > 0 ? '100%' : '0%'),
            background:'var(--acc-dim)', transition:'width 0.2s', zIndex:0
          }} />
          <span style={{position:'relative', zIndex:1}}>
            {pouring ? `POURING — ${poured.toFixed(2)} / ${capDisplay} ${capUnits}` : poured > 0 ? `✓ POURED ${poured.toFixed(1)} ${capUnits}  ·  TAP TO RE-POUR` : `▶ START POUR METER`}
          </span>
        </button>
        <div style={{display:'flex', gap:10}}>
          <button onClick={onBack} style={btnNew}>
            ← NEW QUERY
          </button>
          <button
            onClick={async () => {
              if (wrongState !== 'idle') return;
              setWrongState('sending');
              try {
                const ok = typeof onWrong === 'function' ? await onWrong() : false;
                setWrongState(ok ? 'done' : 'error');
              } catch {
                setWrongState('error');
              }
            }}
            disabled={wrongState === 'sending' || wrongState === 'done'}
            style={btnWrong}
          >
            {wrongState === 'idle' ? 'WRONG SPEC' :
             wrongState === 'sending' ? 'SENDING…' :
             wrongState === 'error' ? 'FAILED — RETRY' :
             'FLAGGED ✓'}
          </button>
        </div>
      </div>
    </div>
  );
}

// ══ JOB TABLE SCREEN ══════════════════════════════════
function JobTableScreen({ data, veh, onBack, onItemTap, units, layout }) {
  const [done, setDone] = useSt(new Set());
  const [expanded, setExpanded] = useSt(null);

  const toggle = (id) => {
    setDone(prev => {
      const next = new Set(prev);
      next.has(id) ? next.delete(id) : next.add(id);
      return next;
    });
  };

  const fluidItems = data.items.filter(i => i.capacity !== null);
  const totalCapQuarts = sumCapacitiesInQuarts(fluidItems);
  const totalLabel = totalCapQuarts == null
    ? null
    : units === 'metric'
      ? (totalCapQuarts * QUART_TO_LITER).toFixed(1) + 'L'
      : totalCapQuarts.toFixed(1) + 'QT';
  const doneCount = data.items.filter(i => done.has(i.id)).length;
  const pct = (doneCount / data.items.length) * 100;

  // group by category
  const grouped = data.items.reduce((acc, item) => {
    (acc[item.category] = acc[item.category] || []).push(item);
    return acc;
  }, {});

  return (
    <div style={{...screenStyle, paddingTop:54}}>
      {/* job header */}
      <div style={{background:'var(--panel)', borderBottom:'3px solid var(--accent)', padding:'12px 16px', flexShrink:0}}>
        <div style={{display:'flex', justifyContent:'space-between', alignItems:'flex-start', marginBottom:6}}>
          <div style={{
            fontFamily:"'DM Mono',monospace", fontSize:8,
            letterSpacing:'0.2em', textTransform:'uppercase',
            color:'var(--black)', background:'var(--accent)', padding:'4px 10px', alignSelf:'flex-start'
          }}>JOB TABLE · FLUID</div>
          <div style={{
            fontFamily:"'DM Mono',monospace", fontSize:8,
            letterSpacing:'0.12em', textTransform:'uppercase',
            color:'var(--muted)', border:'1px solid var(--border-h)', padding:'4px 8px'
          }}>FORD WORKSHOP</div>
        </div>
        <div style={{fontFamily:"'DM Mono',monospace", fontSize:9, letterSpacing:'0.18em', textTransform:'uppercase', color:'var(--muted)', marginBottom:3}}>
          {veh.year} {veh.make} {veh.model} · {veh.engine}
        </div>
        <div style={{fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:24, textTransform:'uppercase', letterSpacing:'0.06em', color:'var(--text)', lineHeight:1.05}}>
          {data.jobName}
        </div>
        <div style={{display:'flex', alignItems:'center', gap:10, marginTop:10}}>
          <div style={{fontFamily:"'DM Mono',monospace", fontSize:10, letterSpacing:'0.12em', color:'var(--accent)'}}>
            {doneCount}/{data.items.length}
          </div>
          <div style={{flex:1, height:4, background:'var(--border-h)'}}>
            <div style={{height:'100%', background:'var(--accent)', width:`${pct}%`, transition:'width 0.3s'}} />
          </div>
          <div style={{fontFamily:"'DM Mono',monospace", fontSize:10, letterSpacing:'0.12em', color:'var(--muted)'}}>
            {totalLabel ? `${totalLabel} TOTAL` : 'TOTAL N/A'}
          </div>
        </div>
      </div>

      {/* table */}
      <div style={{flex:1, overflowY:'auto', WebkitOverflowScrolling:'touch'}}>
        {Object.entries(grouped).map(([cat, items]) => (
          <React.Fragment key={cat}>
            <div style={{
              padding:'8px 16px 6px',
              background:'var(--panel-2)',
              borderBottom:'1px solid var(--border)',
              borderTop:'2px solid var(--border)',
              fontFamily:"'DM Mono',monospace", fontSize:8,
              letterSpacing:'0.22em', textTransform:'uppercase',
              color:'var(--muted)',
              display:'flex', alignItems:'center', gap:8
            }}>
              <span style={{display:'inline-block', width:3, height:10, background:'var(--accent)', borderRadius:1}} />
              {cat}
            </div>
            {items.map(item => (
              <JobRow
                key={item.id}
                item={item}
                done={done.has(item.id)}
                onToggle={() => toggle(item.id)}
                onExpand={() => setExpanded(expanded === item.id ? null : item.id)}
                expanded={expanded === item.id}
                layout={layout}
                units={units}
              />
            ))}
          </React.Fragment>
        ))}
      </div>

      {/* bottom */}
      <div style={{flexShrink:0, padding:'12px 16px 16px', borderTop:'2px solid var(--border)', background:'var(--panel)', display:'flex', gap:10}}>
        <button onClick={onBack} style={{
          flex:1, height:60, background:'var(--panel-2)',
          border:'2px solid var(--border-h)', color:'var(--text)',
          fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:17,
          letterSpacing:'0.14em', textTransform:'uppercase', cursor:'pointer',
          display:'flex', alignItems:'center', justifyContent:'center', gap:10
        }}>← NEW QUERY</button>
        <button onClick={() => setDone(new Set())} style={{
          width:82, height:60, background:'var(--panel-2)',
          border:'2px solid var(--border-h)', color:'var(--mid)',
          fontFamily:"'DM Mono',monospace", fontSize:8,
          letterSpacing:'0.14em', textTransform:'uppercase',
          cursor:'pointer', lineHeight:1.6
        }}>RESET<br/>TABLE</button>
      </div>
    </div>
  );
}

function JobRow({ item, done, onToggle, onExpand, expanded, layout, units }) {
  const hasWarn = item.warning != null;
  const isRed = item.warningLevel === 'red';
  const capacityQuarts = item.capacity == null ? null : capacityToQuarts(item.capacity, item.units);
  const displayCap = item.capacity == null ? null :
    units === 'metric' && capacityQuarts != null
      ? (capacityQuarts * QUART_TO_LITER).toFixed(2)
      : item.capacity.toFixed(1);
  const displayUnits = units === 'metric' && capacityQuarts != null ? 'L' : item.units;

  if (layout === "cards") {
    // card layout — more visual
    return (
      <div style={{
        margin:'10px 12px', padding:'12px 14px',
        background:'var(--panel)',
        border:'2px solid var(--border-h)',
        borderLeft: `4px solid ${isRed ? 'var(--red)' : hasWarn ? 'var(--amber)' : done ? 'var(--dim)' : 'var(--accent)'}`,
        opacity: done ? 0.42 : 1,
        cursor:'pointer'
      }} onClick={onToggle}>
        <div style={{display:'flex', justifyContent:'space-between', alignItems:'flex-start', gap:10}}>
          <div style={{flex:1}}>
            <div style={{fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:18, color:'var(--text)', textTransform:'uppercase', letterSpacing:'0.05em', lineHeight:1.1}}>
              {item.name}
            </div>
            <div style={{fontFamily:"'DM Mono',monospace", fontSize:10, color:'var(--text-d)', letterSpacing:'0.06em', marginTop:4}}>
              {item.spec}
            </div>
            <div style={{fontFamily:"'DM Mono',monospace", fontSize:9, color:'var(--muted)', letterSpacing:'0.04em', marginTop:2}}>
              {item.specDetail}
            </div>
          </div>
          <div style={{textAlign:'right'}}>
            {displayCap != null ? (
              <>
                <div style={{fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:38, color:'var(--accent)', lineHeight:0.88, letterSpacing:'-0.01em'}}>
                  {displayCap}
                </div>
                <div style={{fontFamily:"'DM Mono',monospace", fontSize:9, color:'var(--muted)', letterSpacing:'0.12em', marginTop:3}}>
                  {displayUnits}
                </div>
              </>
            ) : (
              <div style={{fontFamily:"'DM Mono',monospace", fontSize:9, color:'var(--dim)', letterSpacing:'0.12em'}}>—</div>
            )}
          </div>
        </div>
        {hasWarn && (
          <div style={{
            marginTop:8, padding:'6px 10px',
            background: isRed ? 'rgba(255,51,51,0.1)' : 'rgba(245,166,35,0.1)',
            border:`1px solid ${isRed ? 'rgba(255,51,51,0.3)' : 'rgba(245,166,35,0.3)'}`,
            fontFamily:"'DM Mono',monospace", fontSize:9,
            color: isRed ? 'var(--red)' : 'var(--amber)',
            letterSpacing:'0.1em', textTransform:'uppercase'
          }}>
            ⚠ {item.warning}
          </div>
        )}
      </div>
    );
  }

  // default dense table layout
  return (
    <div style={{
      display:'grid',
      gridTemplateColumns: '36px 1fr 92px',
      borderBottom:'1px solid var(--border)',
      borderLeft: `3px solid ${isRed ? 'var(--red)' : hasWarn ? 'var(--amber)' : 'transparent'}`,
      opacity: done ? 0.42 : 1,
      cursor:'pointer',
      background: done ? 'transparent' : 'transparent'
    }} onClick={onToggle}>
      <div style={{display:'flex', alignItems:'center', justifyContent:'center', borderRight:'1px solid var(--border)'}}>
        <div style={{
          width:22, height:22,
          border:'2px solid var(--border-h)',
          display:'flex', alignItems:'center', justifyContent:'center',
          background: done ? 'var(--accent)' : 'transparent',
          borderColor: done ? 'var(--accent)' : 'var(--border-h)'
        }}>
          {done && <svg width="12" height="12" viewBox="0 0 12 12"><path d="M2 6l3 3 5-6" stroke="#0A0F0A" strokeWidth="2" fill="none" strokeLinecap="round"/></svg>}
        </div>
      </div>
      <div style={{padding:'12px 12px'}}>
        <div style={{fontFamily:"'Barlow Condensed',sans-serif", fontWeight:700, fontSize:17, textTransform:'uppercase', letterSpacing:'0.05em', color:'var(--text)', lineHeight:1.1}}>
          {item.name}
        </div>
        <div style={{fontFamily:"'DM Mono',monospace", fontSize:10, color:'var(--text-d)', letterSpacing:'0.06em', marginTop:3}}>
          {item.spec}
        </div>
        {hasWarn && (
          <div style={{
            marginTop:6, padding:'4px 8px',
            background: isRed ? 'rgba(255,51,51,0.12)' : 'rgba(245,166,35,0.12)',
            border: `1px solid ${isRed ? 'rgba(255,51,51,0.4)' : 'rgba(245,166,35,0.35)'}`,
            fontFamily:"'DM Mono',monospace", fontSize:8,
            color: isRed ? 'var(--red)' : 'var(--amber)',
            letterSpacing:'0.08em', textTransform:'uppercase',
            fontWeight: isRed ? 500 : 400,
            animation: isRed ? 'fbf-pulse 1.6s ease-in-out infinite' : 'none'
          }}>
            ⚠ {item.warning}
          </div>
        )}
        <div style={{fontFamily:"'DM Mono',monospace", fontSize:9, color:'var(--muted)', letterSpacing:'0.04em', lineHeight:1.5, marginTop:4}}>
          {item.procedure}
        </div>
      </div>
      <div style={{display:'flex', flexDirection:'column', alignItems:'flex-end', justifyContent:'center', padding:'12px 12px 12px 4px', minWidth:0, overflow:'hidden'}}>
        {displayCap != null ? (
          <>
            <div style={{fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:36, color:'var(--accent)', lineHeight:0.88, letterSpacing:'-0.01em', whiteSpace:'nowrap'}}>
              {displayCap}
            </div>
            <div style={{fontFamily:"'DM Mono',monospace", fontSize:8, color:'var(--muted)', letterSpacing:'0.1em', marginTop:3, textAlign:'right'}}>
              {displayUnits}
            </div>
          </>
        ) : (
          <div style={{fontFamily:"'DM Mono',monospace", fontSize:9, color:'var(--dim)', letterSpacing:'0.12em'}}>N/A</div>
        )}
      </div>
    </div>
  );
}

// ══ CAPACITY-ONLY SCREEN ══════════════════════════════
function CapacityScreen({ data, veh, onBack, onWrong, units, density }) {
  const [flagState, setFlagState] = useSt('idle'); // idle | sending | done | error
  const canFlag = typeof onWrong === 'function' && !!data.fluidSpecId;
  const hasCapacity = data.hasCapacity !== false && data.capacity && data.capacity.value > 0;
  const val = hasCapacity
    ? (units === 'metric' ? data.capacity.metric.toFixed(2) : data.capacity.value.toFixed(1))
    : '';
  const u = hasCapacity ? (units === 'metric' ? 'L' : data.capacity.units) : '';
  const isEstimate = !!data.isEstimate;
  const accentColor = isEstimate ? '#FF9500' : 'var(--accent)';
  const accentGlow = isEstimate ? 'rgba(255,149,0,0.55)' : 'var(--acc-glow)';
  const fluidType = typeof data.fluidType === 'string' && data.fluidType.trim()
    ? data.fluidType.trim().toUpperCase()
    : '';
  // Alex: fluid type is primary. If we have it, it headlines — capacity drops
  // to subhead. If we have no fluid type but do have capacity (legacy path),
  // capacity takes the headline. Brake-without-capacity: fluid type only.
  const fluidTypeIsHeadline = !!fluidType;
  const serviceTorque = Array.isArray(data.serviceTorque) ? data.serviceTorque : [];
  const withFilter = (data.capacity && data.capacity.withFilter) || null;
  const withoutFilter = (data.capacity && data.capacity.withoutFilter) || null;
  const hasCapacitySplit = !!(withFilter || withoutFilter);
  // Alex: when OEM publishes both with-filter and without-filter capacities
  // (engine oil, typically), show BOTH. Averaging them hides the distinction a
  // mechanic actually needs at the drain pan.
  const splitRows = [];
  if (withFilter) splitRows.push({ label: 'W/ FILTER', pair: withFilter });
  if (withoutFilter) splitRows.push({ label: 'W/O FILTER', pair: withoutFilter });
  const alternatives = Array.isArray(data.fluidTypeAlternatives)
    ? data.fluidTypeAlternatives.filter((s) => typeof s === 'string' && s.trim()).map((s) => s.trim().toUpperCase())
    : [];

  return (
    <div style={{...screenStyle, paddingTop:54, display:'flex', flexDirection:'column'}}>
      <div style={{background:'var(--panel)', borderBottom:'2px solid var(--border)', padding:'11px 16px', flexShrink:0}}>
        <div style={microLabel}>Capacity · Voice Answer</div>
        <div style={{fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:19, textTransform:'uppercase', letterSpacing:'0.06em', color:'var(--text)', lineHeight:1.1}}>
          {veh.year} {veh.make} {veh.model}
        </div>
        <div style={{fontFamily:"'Barlow Condensed',sans-serif", fontWeight:700, fontSize:14, textTransform:'uppercase', letterSpacing:'0.08em', color:'var(--mid)', marginTop:1}}>
          {veh.engine}
        </div>
      </div>

      <div style={{flex:1, overflowY:'auto', display:'flex', flexDirection:'column', alignItems:'center', padding:'18px 16px 10px', position:'relative'}}>
        <SideRail />
        {isEstimate && (
          <span style={{
            fontFamily:"'DM Mono',monospace", fontSize:9, fontWeight:700,
            letterSpacing:'0.22em', textTransform:'uppercase',
            padding:'6px 12px', border:'2px solid #FF9500',
            background:'rgba(255,149,0,0.1)', color:'#FF9500',
            marginBottom:10
          }}>AI ESTIMATE</span>
        )}
        <div style={{fontFamily:"'DM Mono',monospace", fontSize:11, letterSpacing:'0.24em', textTransform:'uppercase', color:'var(--muted)', marginBottom:6}}>
          "{data.query}"
        </div>
        <div style={{fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:20, textTransform:'uppercase', letterSpacing:'0.08em', color:'var(--text-d)', marginBottom:14}}>
          {data.component}
        </div>

        {/* FLUID TYPE — Alex-rule headline. Large, bold, primary accent, 2-line clamp. */}
        {fluidTypeIsHeadline && (
          <div style={{
            fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900,
            fontSize:'clamp(40px, 11vw, 60px)',
            lineHeight:0.92, color:accentColor,
            letterSpacing:'0.01em', textTransform:'uppercase',
            textAlign:'center', width:'100%',
            maxWidth:380,
            textShadow:`0 0 36px ${accentGlow}`,
            display:'-webkit-box',
            WebkitLineClamp:2, WebkitBoxOrient:'vertical',
            overflow:'hidden'
          }}>
            {fluidType}
          </div>
        )}

        {/* ALSO ACCEPTABLE — OEM-approved alternate viscosities inline. Smaller
            than the headline but still readable. Only renders when the OEM
            explicitly approves 1+ alternates. Not rendered as an empty label. */}
        {fluidTypeIsHeadline && alternatives.length > 0 && (
          <div style={{
            marginTop:8,
            fontFamily:"'Barlow Condensed',sans-serif", fontWeight:700,
            fontSize: 'clamp(14px, 3.8vw, 17px)',
            letterSpacing:'0.1em', textTransform:'uppercase',
            color: isEstimate ? 'rgba(255,149,0,0.82)' : 'var(--mid)',
            textAlign:'center', maxWidth:340, lineHeight:1.25
          }}>
            <span style={{color:'var(--muted)', marginRight:6}}>ALSO ACCEPTABLE:</span>
            <span style={{color: accentColor, opacity: 0.82}}>
              {alternatives.join(', ')}
            </span>
          </div>
        )}

        {/* CAPACITY — either split rows (W/ FILTER, W/O FILTER) when OEM
            publishes both values, or a single subhead otherwise. */}
        {hasCapacitySplit ? (
          <div style={{
            width:'100%', maxWidth:340,
            marginTop: fluidTypeIsHeadline ? 18 : 8,
            display:'flex', flexDirection:'column', gap:6,
            alignItems:'stretch'
          }}>
            {splitRows.map((row) => {
              const primaryQt = typeof row.pair.quarts === 'number' ? row.pair.quarts : null;
              const primaryL = typeof row.pair.liters === 'number' ? row.pair.liters : null;
              const qtStr = primaryQt != null ? primaryQt.toFixed(2) : '—';
              const lStr = primaryL != null ? primaryL.toFixed(2) : '—';
              return (
                <div key={row.label} style={{
                  display:'flex', alignItems:'baseline', justifyContent:'space-between',
                  padding:'6px 2px',
                  borderTop: '1px solid var(--border)',
                }}>
                  <div style={{
                    fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900,
                    fontSize: 'clamp(18px, 5vw, 22px)',
                    color:'var(--text)',
                    textTransform:'uppercase', letterSpacing:'0.1em',
                  }}>{row.label}</div>
                  <div style={{
                    display:'flex', alignItems:'baseline', gap:10,
                    fontFamily:"'DM Mono',monospace", fontVariantNumeric:'tabular-nums',
                  }}>
                    <span style={{
                      fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900,
                      fontSize:'clamp(28px, 8vw, 40px)',
                      color: accentColor, letterSpacing:'0.02em',
                      textShadow: `0 0 28px ${accentGlow}`,
                    }}>{qtStr}</span>
                    <span style={{
                      fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900,
                      fontSize: 'clamp(14px, 4vw, 18px)',
                      color: accentColor, opacity:0.7,
                      letterSpacing:'0.08em', textTransform:'uppercase'
                    }}>QT</span>
                    <span style={{
                      fontFamily:"'DM Mono',monospace", fontSize: 12,
                      color:'var(--muted)', letterSpacing:'0.08em',
                      whiteSpace:'nowrap'
                    }}>{lStr} L</span>
                  </div>
                </div>
              );
            })}
          </div>
        ) : (
          <>
            {/* CAPACITY + UNIT — single subhead. Same bold weight, muted accent. */}
            {hasCapacity && (
              <div style={{
                display:'flex', alignItems:'baseline', justifyContent:'center',
                gap:10, marginTop: fluidTypeIsHeadline ? 14 : 6
              }}>
                <div style={{
                  fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900,
                  fontSize: fluidTypeIsHeadline ? 'clamp(52px, 15vw, 80px)' : 'clamp(110px, 34vw, 170px)',
                  lineHeight:0.88, color:accentColor,
                  opacity: fluidTypeIsHeadline ? 0.62 : 1,
                  letterSpacing:'-0.02em',
                  textShadow: fluidTypeIsHeadline ? 'none' : `0 0 70px ${accentGlow}`
                }}>{val}</div>
                <div style={{
                  fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900,
                  fontSize: fluidTypeIsHeadline ? 'clamp(28px, 8vw, 42px)' : 38,
                  color:accentColor,
                  opacity: fluidTypeIsHeadline ? 0.62 : 1,
                  textTransform:'uppercase', letterSpacing:'0.08em',
                  lineHeight:1
                }}>{u}</div>
              </div>
            )}

            {/* ALSO row — alternate unit. Not rendered when split rows already
                show both metric and US per-line. */}
            {hasCapacity && (
              <div style={{marginTop:10, display:'flex', gap:6, flexWrap:'wrap', justifyContent:'center'}}>
                {!isEstimate && (
                  <Flag kind="blue">ALSO: {units === 'metric' ? data.capacity.value + ' QT' : data.capacity.metric.toFixed(2) + ' L'}</Flag>
                )}
                {isEstimate && (
                  <Flag kind="amber">ALSO: {units === 'metric' ? data.capacity.value + ' QT' : data.capacity.metric.toFixed(2) + ' L'}</Flag>
                )}
              </div>
            )}
          </>
        )}

        {/* DRAIN / FILL PLUG — bundle torque on fluid-service answers */}
        {serviceTorque.length > 0 && (
          <div style={{
            width:'100%', maxWidth:340,
            marginTop:18, padding:'10px 14px',
            background:'var(--panel)',
            border:'2px solid var(--border-h)',
            borderLeft:'4px solid var(--accent)'
          }}>
            <div style={{...microLabel, marginBottom:8}}>Drain / Fill Plug</div>
            {serviceTorque.map((t, i) => (
              <div key={i} style={{
                display:'flex', justifyContent:'space-between', alignItems:'baseline',
                padding:'4px 0',
                borderTop: i === 0 ? 'none' : '1px solid var(--border)'
              }}>
                <div style={{
                  fontFamily:"'Barlow Condensed',sans-serif", fontWeight:700,
                  fontSize:15, color:'var(--text)',
                  textTransform:'uppercase', letterSpacing:'0.05em',
                  lineHeight:1.15, flex:1, minWidth:0, paddingRight:10
                }}>
                  {t.component}
                </div>
                <div style={{textAlign:'right', whiteSpace:'nowrap'}}>
                  {t.valueLbft != null && (
                    <span style={{
                      fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900,
                      fontSize:22, color:'var(--accent)',
                      letterSpacing:'0.02em'
                    }}>
                      {t.valueLbft} LB-FT
                    </span>
                  )}
                  {t.valueNm != null && (
                    <span style={{
                      fontFamily:"'DM Mono',monospace", fontSize:10,
                      color:'var(--muted)', letterSpacing:'0.1em',
                      marginLeft:8
                    }}>
                      {t.valueNm} NM
                    </span>
                  )}
                </div>
              </div>
            ))}
          </div>
        )}

        {data.note && (
          <div style={{fontFamily:"'DM Mono',monospace", fontSize:12, color:'var(--text-d)', letterSpacing:'0.08em', marginTop:16, textAlign:'center', maxWidth:340, lineHeight:1.5}}>
            {data.note}
          </div>
        )}

        {isEstimate && data.confidenceNote && (
          <div style={{
            fontFamily:"'DM Mono',monospace", fontSize:10,
            color:'#FF9500', letterSpacing:'0.08em',
            marginTop:10, textAlign:'center', maxWidth:340, lineHeight:1.5,
            opacity:0.85
          }}>
            {data.confidenceNote}
          </div>
        )}

        {!isEstimate && (
          <div style={{marginTop:18, textAlign:'center'}}>
            <OlpCredit />
          </div>
        )}
      </div>

      <div style={{flexShrink:0, padding:'12px 16px 16px', borderTop:'2px solid var(--border)', background:'var(--panel)', display:'flex', flexDirection:'column', gap:8}}>
        <button onClick={onBack} style={{
          width:'100%', height:66, background:'var(--panel-2)',
          border:'2px solid var(--border-h)', color:'var(--text)',
          fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:18,
          letterSpacing:'0.14em', textTransform:'uppercase', cursor:'pointer'
        }}>← NEW QUERY</button>
        {canFlag && (
          <button
            onClick={async () => {
              if (flagState !== 'idle') return;
              setFlagState('sending');
              try {
                const ok = await onWrong();
                setFlagState(ok ? 'done' : 'error');
              } catch {
                setFlagState('error');
              }
            }}
            disabled={flagState === 'sending' || flagState === 'done'}
            style={{
              width:'100%', height:36, background:'transparent',
              border:'1px solid rgba(255,51,51,0.5)',
              color: flagState === 'done' ? 'var(--mid)' : 'rgba(255,51,51,0.55)',
              fontFamily:"'DM Mono',monospace", fontWeight:500, fontSize:11,
              letterSpacing:'0.22em', textTransform:'uppercase',
              cursor: flagState === 'idle' || flagState === 'error' ? 'pointer' : 'default',
              opacity: flagState === 'idle' || flagState === 'error' ? 0.55 : 0.85,
            }}
          >
            {flagState === 'idle' ? 'FLAG AS WRONG' :
             flagState === 'sending' ? 'FLAGGING…' :
             flagState === 'error' ? 'FAILED — RETRY' :
             'THANKS — FLAGGED'}
          </button>
        )}
      </div>
    </div>
  );
}

// ══ SAFETY WALL (blocking warning) ═══════════════════
function SafetyWall({ data, onAck }) {
  return (
    <div style={{
      ...screenStyle, paddingTop:54,
      background:'var(--black)',
      display:'flex', flexDirection:'column',
      animation:'fbf-shake 0.4s ease-in-out'
    }}>
      <div style={{flex:1, display:'flex', flexDirection:'column', padding:'20px 16px', overflowY:'auto'}}>
        <div style={{
          fontFamily:"'DM Mono',monospace", fontSize:10,
          letterSpacing:'0.28em', textTransform:'uppercase',
          color:'var(--red)', marginBottom:12
        }}>⚠⚠⚠ {data.severity} ⚠⚠⚠</div>

        <div style={{
          background:'var(--red)', color:'var(--black)',
          padding:'22px 16px', marginBottom:16,
          animation:'fbf-pulse 1s ease-in-out infinite'
        }}>
          <div style={{
            fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900,
            fontSize:52, lineHeight:0.88, letterSpacing:'-0.01em',
            textTransform:'uppercase'
          }}>{data.title}</div>
          <div style={{
            fontFamily:"'Barlow Condensed',sans-serif", fontWeight:700,
            fontSize:18, marginTop:8, textTransform:'uppercase', letterSpacing:'0.06em'
          }}>{data.subtitle}</div>
        </div>

        <div style={{
          padding:'14px 16px', marginBottom:14,
          background:'rgba(255,51,51,0.07)',
          border:'2px solid rgba(255,51,51,0.4)'
        }}>
          <div style={{fontFamily:"'DM Mono',monospace", fontSize:10, letterSpacing:'0.16em', textTransform:'uppercase', color:'var(--red)', marginBottom:6}}>
            REASON
          </div>
          <div style={{fontFamily:"'Barlow',sans-serif", fontSize:16, color:'var(--text)', lineHeight:1.5, fontWeight:500}}>
            {data.reason}
          </div>
        </div>

        <div style={{
          padding:'14px 16px',
          background:'var(--panel)',
          border:'2px solid var(--border-h)',
          borderLeft:'4px solid var(--accent)'
        }}>
          <div style={{fontFamily:"'DM Mono',monospace", fontSize:10, letterSpacing:'0.16em', textTransform:'uppercase', color:'var(--accent)', marginBottom:6}}>
            ✓ CORRECT FLUID
          </div>
          <div style={{fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:28, color:'var(--text)', textTransform:'uppercase', letterSpacing:'0.04em'}}>
            {data.correct}
          </div>
        </div>
      </div>

      <div style={{flexShrink:0, padding:'12px 16px 16px', background:'var(--panel)', borderTop:'2px solid var(--red)'}}>
        <button onClick={onAck} style={{
          width:'100%', height:72, background:'transparent',
          border:'3px solid var(--red)', color:'var(--red)',
          fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:20,
          letterSpacing:'0.14em', textTransform:'uppercase', cursor:'pointer'
        }}>I UNDERSTAND — ACKNOWLEDGE</button>
      </div>
    </div>
  );
}

// ══ shared styles ════════════════════════════════════
const screenStyle = {
  position:'absolute', inset:0,
  display:'flex', flexDirection:'column',
  background:'var(--bg)'
};

const microLabel = {
  fontFamily:"'DM Mono',monospace", fontSize:9,
  letterSpacing:'0.22em', textTransform:'uppercase', color:'var(--muted)'
};

const diagBlock = {
  width:'100%', background:'var(--panel)',
  border:'2px solid var(--border-h)',
  borderLeft:'4px solid var(--accent)'
};

const btnNew = {
  flex:1, height:64, background:'var(--panel-2)',
  border:'2px solid var(--border-h)', color:'var(--text)',
  fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:17,
  letterSpacing:'0.14em', textTransform:'uppercase', cursor:'pointer'
};

const btnWrong = {
  flex:1, height:64, background:'transparent',
  border:'2px solid rgba(255,59,48,0.46)', color:'var(--warn)',
  fontFamily:"'Barlow Condensed',sans-serif", fontWeight:900, fontSize:17,
  letterSpacing:'0.14em', textTransform:'uppercase', cursor:'pointer'
};

Object.assign(window, {
  ListenScreen, SingleFluidScreen, JobTableScreen, CapacityScreen, SafetyWall
});
