// screens-immo.jsx — Immobilien dashboard, search builder wizard, search results

// ─── DASHBOARD ──────────────────────────────────────────────────────────
function DashboardScreen({ ctx }) {
  const { listings, searches, navigate, favs, toggleFav, notifBadge } = ctx;
  const purchaseSearches = searches.filter(s => s.category === 'kauf');
  const bestDeals = listings
    .filter(l => l.type === 'kauf' && l.aiScore)
    .sort((a, b) => b.aiScore - a.aiScore)
    .slice(0, 4);
  const stats = {
    active: purchaseSearches.filter(s => s.active).length,
    matches: purchaseSearches.reduce((sum, s) => sum + s.matches, 0),
    newToday: purchaseSearches.reduce((sum, s) => sum + s.newToday, 0),
    avgScore: Math.round(listings.filter(l => l.aiScore).reduce((s, l) => s + l.aiScore, 0) / listings.filter(l => l.aiScore).length),
  };

  return (
    <div className="phone-scroll fade-in" style={{ paddingBottom: 100, background: 'var(--bg)' }}>
      {/* Header */}
      <div style={{ padding: '60px 20px 0' }}>
        <div style={{ display: 'flex', justifyContent: 'space-between', alignItems: 'flex-start' }}>
          <div>
            <div style={{ fontSize: 13, color: 'var(--ink-muted)', fontWeight: 500 }}>
              Guten Morgen, Maxim
            </div>
            <h1 style={{ margin: '6px 0 0', fontFamily: 'var(--font-display)', fontWeight: 400, fontSize: 38, lineHeight: 1.0, letterSpacing: -0.025 }}>
              Kaufobjekte
            </h1>
          </div>
          <div style={{ display: 'flex', gap: 8 }}>
            <IconBtn onClick={() => navigate('swipe')}><I.swipe /></IconBtn>
            <IconBtn onClick={() => navigate('admin')}><I.settings /></IconBtn>
          </div>
        </div>
      </div>

      {/* Stats grid */}
      <div style={{ padding: '20px 16px 0', display: 'grid', gridTemplateColumns: '1fr 1fr', gap: 10 }}>
        <StatTile value={stats.active} label="Aktive Suchen" />
        <StatTile value={stats.matches} label="Treffer gesamt" />
        <StatTile value={`+${stats.newToday}`} label="Neu heute" delta="seit Mitternacht" accent />
        <StatTile value={`Ø ${stats.avgScore}`} label="KI-Score Mittelw." />
      </div>

      {/* New search CTA */}
      <div style={{ padding: '24px 16px 0' }}>
        <button
          onClick={() => navigate('searchBuilder')}
          style={{
            width: '100%', background: 'var(--ink)', color: '#fff',
            border: 0, borderRadius: 'var(--r-lg)', padding: '20px',
            display: 'flex', alignItems: 'center', gap: 14, cursor: 'pointer',
            textAlign: 'left',
            boxShadow: '0 4px 16px rgba(31,26,20,.15)',
          }}
        >
          <div style={{
            width: 44, height: 44, borderRadius: 12, background: 'var(--primary)',
            display: 'flex', alignItems: 'center', justifyContent: 'center', flexShrink: 0,
          }}>
            <I.plus style={{ width: 24, height: 24, strokeWidth: 2.5 }} />
          </div>
          <div style={{ flex: 1 }}>
            <div style={{ fontSize: 16, fontWeight: 700, letterSpacing: -0.01 }}>Neue Kaufsuche anlegen</div>
            <div style={{ fontSize: 12, color: 'rgba(255,255,255,.6)', marginTop: 2 }}>
              In 4 Schritten — wir scannen ab sofort für Sie.
            </div>
          </div>
          <I.chevR style={{ opacity: .6 }} />
        </button>
      </div>

      {/* Active searches */}
      <Section title="Ihre Suchen" trailing={`${purchaseSearches.length} insgesamt`}>
        <div style={{ display: 'flex', flexDirection: 'column', gap: 10 }}>
          {purchaseSearches.map(s => (
            <SearchCard key={s.id} search={s} onTap={() => navigate('results', { searchId: s.id })} />
          ))}
        </div>
      </Section>

      {/* Best deals */}
      <Section title="Beste KI-Bewertungen" trailing="Alle ansehen" onTrailing={() => navigate('results', { searchId: purchaseSearches[0]?.id })}>
        <div style={{ display: 'flex', flexDirection: 'column', gap: 8 }}>
          {bestDeals.map((l, i) => (
            <ListingRow key={l.id} listing={l} rank={i+1} onTap={() => navigate('listing', { id: l.id })} />
          ))}
        </div>
      </Section>

      {/* Debug / Task limits */}
      <Section title="System">
        <div className="card" style={{ padding: 16 }}>
          <div style={{ display: 'flex', justifyContent: 'space-between', alignItems: 'center', marginBottom: 12 }}>
            <div style={{ fontSize: 14, fontWeight: 600 }}>Tageskontingent</div>
            <span className="chip chip-success">Aktiv</span>
          </div>
          <div style={{ marginBottom: 10 }}>
            <div style={{ display: 'flex', justifyContent: 'space-between', fontSize: 12, color: 'var(--ink-muted)', marginBottom: 4 }}>
              <span>KI-Bewertungen heute</span>
              <span style={{ fontWeight: 700, color: 'var(--ink)' }}>23 / 100</span>
            </div>
            <div style={{ height: 6, background: 'var(--surface-2)', borderRadius: 999, overflow: 'hidden' }}>
              <div style={{ width: '23%', height: '100%', background: 'var(--primary)', borderRadius: 999 }} />
            </div>
          </div>
          <div>
            <div style={{ display: 'flex', justifyContent: 'space-between', fontSize: 12, color: 'var(--ink-muted)', marginBottom: 4 }}>
              <span>Scrape-Anfragen</span>
              <span style={{ fontWeight: 700, color: 'var(--ink)' }}>412 / 2000</span>
            </div>
            <div style={{ height: 6, background: 'var(--surface-2)', borderRadius: 999, overflow: 'hidden' }}>
              <div style={{ width: '21%', height: '100%', background: 'var(--info)', borderRadius: 999 }} />
            </div>
          </div>
          <button
            onClick={() => navigate('admin')}
            style={{
              marginTop: 12, background: 'var(--surface-2)', border: 0, color: 'var(--ink)',
              padding: '10px 14px', borderRadius: 999, fontSize: 13, fontWeight: 600, cursor: 'pointer',
              width: '100%',
            }}
          >
            Job-Monitor öffnen
          </button>
        </div>
      </Section>
    </div>
  );
}

function IconBtn({ children, onClick, badge }) {
  return (
    <button onClick={onClick} style={{
      width: 40, height: 40, borderRadius: 999, border: 0, background: 'var(--surface)',
      display: 'flex', alignItems: 'center', justifyContent: 'center',
      cursor: 'pointer', color: 'var(--ink)',
      boxShadow: '0 1px 4px rgba(0,0,0,.06)', position: 'relative',
    }}>
      {children}
      {badge > 0 && (
        <div style={{
          position: 'absolute', top: -2, right: -2,
          background: 'var(--danger)', color: '#fff', fontSize: 9, fontWeight: 800,
          minWidth: 16, height: 16, padding: '0 4px', borderRadius: 999,
          display: 'flex', alignItems: 'center', justifyContent: 'center',
          boxShadow: '0 0 0 2px var(--bg)',
        }}>{badge}</div>
      )}
    </button>
  );
}

function Section({ title, trailing, onTrailing, children }) {
  return (
    <div style={{ padding: '28px 16px 0' }}>
      <div style={{ display: 'flex', justifyContent: 'space-between', alignItems: 'baseline', padding: '0 4px 12px', gap: 12 }}>
        <div style={{ fontFamily: 'var(--font-display)', fontSize: 22, fontWeight: 400, color: 'var(--ink)', letterSpacing: -0.01, whiteSpace: 'nowrap', overflow: 'hidden', textOverflow: 'ellipsis', minWidth: 0 }}>
          {title}
        </div>
        {trailing && (
          <button
            onClick={onTrailing}
            style={{
              background: 'transparent', border: 0,
              fontSize: 12, fontWeight: 600, color: 'var(--ink-muted)', cursor: 'pointer',
              padding: 4, whiteSpace: 'nowrap', flexShrink: 0,
            }}
          >
            {trailing}
          </button>
        )}
      </div>
      {children}
    </div>
  );
}

function SearchCard({ search, onTap }) {
  return (
    <div className="card" onClick={onTap} style={{ padding: '14px 16px', cursor: 'pointer' }}>
      <div style={{ display: 'flex', justifyContent: 'space-between', alignItems: 'flex-start' }}>
        <div style={{ flex: 1 }}>
          <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginBottom: 4 }}>
            <span style={{
              width: 8, height: 8, borderRadius: 999,
              background: search.active ? 'var(--success)' : 'var(--ink-faint)',
              boxShadow: search.active ? '0 0 0 3px rgba(47,143,90,.18)' : 'none',
            }} />
            <div style={{ fontSize: 15, fontWeight: 700, color: 'var(--ink)', letterSpacing: -0.01 }}>{search.name}</div>
          </div>
          <div style={{ fontSize: 12, color: 'var(--ink-muted)' }}>
            {search.city} +{search.radius}km · {fmtPriceShort(search.priceMin)}–{fmtPriceShort(search.priceMax)} · {search.roomsMin}–{search.roomsMax} Zi.
          </div>
        </div>
        <I.chevR style={{ color: 'var(--ink-faint)' }} />
      </div>
      <div style={{ display: 'flex', gap: 6, marginTop: 12, alignItems: 'center', flexWrap: 'wrap' }}>
        <span className="chip" style={{ fontSize: 11 }}>
          <strong style={{ color: 'var(--ink)' }}>{search.matches}</strong>&nbsp;Treffer
        </span>
        {search.newToday > 0 && (
          <span className="chip chip-accent" style={{ fontSize: 11 }}>+{search.newToday} neu</span>
        )}
        {search.aiEnabled && (
          <span className="chip chip-info" style={{ fontSize: 11 }}>KI</span>
        )}
        <span style={{ fontSize: 11, color: 'var(--ink-faint)', marginLeft: 'auto' }}>
          {fmtRelative(search.lastRun)}
        </span>
      </div>
    </div>
  );
}

// ─── SEARCH BUILDER WIZARD (4 steps) ───────────────────────────────────
function SearchBuilderScreen({ ctx, onDone, type = 'kauf' }) {
  const { navigate, back, addSearch } = ctx;
  const [step, setStep] = React.useState(1);
  const [data, setData] = React.useState({
    name: '',
    type,
    city: 'Berlin',
    radius: 10,
    priceMin: type === 'kauf' ? 250000 : 800,
    priceMax: type === 'kauf' ? 550000 : 1800,
    roomsMin: 2, roomsMax: 4,
    areaMin: 60, areaMax: 120,
    keywords: [],
    excludeKeywords: [],
    platforms: ['immoscout24', 'kleinanzeigen'],
    aiEnabled: type === 'kauf',
  });
  const total = 4;

  const update = (k, v) => setData(d => ({ ...d, [k]: v }));
  const next = () => step < total ? setStep(step + 1) : finish();
  const prev = () => step > 1 ? setStep(step - 1) : back();
  const finish = () => {
    const id = 's_' + Math.random().toString(36).slice(2, 7);
    const newSearch = {
      id, ...data,
      active: true,
      createdAt: new Date().toISOString().slice(0, 10),
      lastRun: new Date().toISOString(),
      matches: 0, newToday: 0,
      category: data.type,
    };
    if (!newSearch.name) newSearch.name = `${data.type === 'kauf' ? 'Kauf' : 'Miete'} ${data.city}`;
    addSearch(newSearch);
    if (data.type === 'miete') {
      navigate('mietenResults', { searchId: id }, true);
    } else {
      navigate('results', { searchId: id }, true);
    }
  };

  return (
    <div style={{ height: '100%', display: 'flex', flexDirection: 'column', background: 'var(--bg)' }}>
      <TopBar
        title={`Schritt ${step}/${total}`} onBack={prev}
        trailing={<button onClick={back} style={{ background: 'transparent', border: 0, color: 'var(--ink-muted)', fontSize: 14, fontWeight: 600, cursor: 'pointer' }}>Abbrechen</button>}
      />
      {/* Progress */}
      <div style={{ padding: '0 20px' }}>
        <div style={{ display: 'flex', gap: 6 }}>
          {[1,2,3,4].map(i => (
            <div key={i} style={{
              flex: 1, height: 4, borderRadius: 999,
              background: i <= step ? 'var(--primary)' : 'var(--border)',
              transition: 'background .3s ease',
            }} />
          ))}
        </div>
      </div>

      <div className="phone-scroll fade-in" key={step} style={{ flex: 1, padding: '24px 20px 120px' }}>
        {step === 1 && <BuilderStep1 data={data} update={update} />}
        {step === 2 && <BuilderStep2 data={data} update={update} />}
        {step === 3 && <BuilderStep3 data={data} update={update} />}
        {step === 4 && <BuilderStep4 data={data} update={update} />}
      </div>

      {/* Footer */}
      <div style={{
        position: 'absolute', bottom: 0, left: 0, right: 0, zIndex: 30,
        padding: '14px 20px 36px',
        background: 'linear-gradient(0deg, var(--bg) 60%, transparent)',
      }}>
        <button onClick={next} className="btn btn-primary" style={{ width: '100%', padding: '16px', fontSize: 16 }}>
          {step < total ? 'Weiter' : 'Suche speichern'}
          <I.chevR style={{ marginLeft: 6 }} />
        </button>
      </div>
    </div>
  );
}

function StepHeader({ overline, title, subtitle }) {
  return (
    <div style={{ marginBottom: 24 }}>
      <div style={{ fontSize: 12, fontWeight: 700, color: 'var(--primary)', letterSpacing: 0.05, textTransform: 'uppercase', marginBottom: 8 }}>
        {overline}
      </div>
      <h2 style={{ margin: 0, fontFamily: 'var(--font-display)', fontWeight: 400, fontSize: 32, lineHeight: 1.05, letterSpacing: -0.02 }}>
        {title}
      </h2>
      {subtitle && (
        <p style={{ margin: '10px 0 0', fontSize: 14, color: 'var(--ink-muted)', lineHeight: 1.5 }}>
          {subtitle}
        </p>
      )}
    </div>
  );
}

function BuilderStep1({ data, update }) {
  const cities = ['Berlin', 'Hamburg', 'München', 'Köln', 'Frankfurt am Main', 'Leipzig', 'Dresden', 'Stuttgart'];
  return (
    <div>
      <StepHeader
        overline="Standort"
        title="Wo soll ich suchen?"
        subtitle="Stadt und Umkreis. Sie können mehrere Suchen für unterschiedliche Lagen anlegen."
      />
      <Label>Suchname</Label>
      <Input value={data.name} onChange={v => update('name', v)} placeholder={`z.B. „Altbau ${data.city}"`} />

      <Label style={{ marginTop: 24 }}>Stadt</Label>
      <div style={{ display: 'flex', gap: 8, flexWrap: 'wrap' }}>
        {cities.map(c => (
          <Pill key={c} active={data.city === c} onClick={() => update('city', c)}>{c}</Pill>
        ))}
      </div>

      <Label style={{ marginTop: 24 }}>Umkreis: <strong>{data.radius} km</strong></Label>
      <input
        type="range" min="0" max="50" step="5" value={data.radius}
        onChange={e => update('radius', +e.target.value)}
        style={{ width: '100%', accentColor: 'var(--primary)' }}
      />
      <div style={{ display: 'flex', justifyContent: 'space-between', fontSize: 11, color: 'var(--ink-muted)', marginTop: 2 }}>
        <span>nur Stadt</span><span>25 km</span><span>50 km</span>
      </div>
    </div>
  );
}

function BuilderStep2({ data, update }) {
  const isKauf = data.type === 'kauf';
  return (
    <div>
      <StepHeader
        overline="Budget & Größe"
        title="Welche Maße passen?"
        subtitle="Preis, Zimmer, Wohnfläche. Bereiche statt fester Werte funktionieren am besten."
      />
      <Label>{isKauf ? 'Kaufpreis' : 'Warmmiete'}</Label>
      <RangeRow
        min={data.priceMin} max={data.priceMax}
        onMin={v => update('priceMin', v)} onMax={v => update('priceMax', v)}
        fmt={isKauf ? fmtPriceShort : v => v + ' €'}
        absMin={isKauf ? 50000 : 300} absMax={isKauf ? 2000000 : 4000}
        step={isKauf ? 25000 : 50}
      />
      <Label style={{ marginTop: 24 }}>Zimmer</Label>
      <RangeRow
        min={data.roomsMin} max={data.roomsMax}
        onMin={v => update('roomsMin', v)} onMax={v => update('roomsMax', v)}
        fmt={v => v + ' Zi.'}
        absMin={1} absMax={8}
        step={0.5}
      />
      <Label style={{ marginTop: 24 }}>Wohnfläche</Label>
      <RangeRow
        min={data.areaMin} max={data.areaMax}
        onMin={v => update('areaMin', v)} onMax={v => update('areaMax', v)}
        fmt={v => v + ' m²'}
        absMin={20} absMax={300}
        step={5}
      />
    </div>
  );
}

function BuilderStep3({ data, update }) {
  const toggle = (kw, list, listKey) => {
    const set = new Set(list);
    if (set.has(kw)) set.delete(kw); else set.add(kw);
    update(listKey, [...set]);
  };
  const presets = ['altbau', 'balkon', 'stuck', 'dielen', 'aufzug', 'garten', 'einbauküche', 'saniert', 'erstbezug', 'denkmal'];
  const exPresets = ['erbpacht', 'sanierungsbedürftig', 'wbs', 'möbliert', 'tausch'];

  const [kwInput, setKwInput] = React.useState('');
  const [exInput, setExInput] = React.useState('');

  return (
    <div>
      <StepHeader
        overline="Stichwörter"
        title="Was darf nicht fehlen?"
        subtitle="Suchwörter in Titel oder Beschreibung. Mehrere mit Komma trennen."
      />
      <Label>Muss enthalten</Label>
      <div style={{ display: 'flex', flexWrap: 'wrap', gap: 6, marginBottom: 10 }}>
        {data.keywords.map(k => (
          <span key={k} className="chip chip-success" style={{ paddingRight: 6 }}>
            {k}
            <button onClick={() => toggle(k, data.keywords, 'keywords')} style={{
              background: 'transparent', border: 0, padding: 0, marginLeft: 4, cursor: 'pointer', display: 'flex',
            }}><I.x style={{ width: 14, height: 14, color: 'var(--success)' }} /></button>
          </span>
        ))}
      </div>
      <Input
        value={kwInput} onChange={setKwInput}
        placeholder="Stichwort eingeben + ↵"
        onKeyDown={e => {
          if (e.key === 'Enter' && kwInput.trim()) {
            update('keywords', [...data.keywords, kwInput.trim().toLowerCase()]);
            setKwInput('');
          }
        }}
      />
      <div style={{ display: 'flex', flexWrap: 'wrap', gap: 6, marginTop: 8 }}>
        {presets.filter(p => !data.keywords.includes(p)).map(p => (
          <button key={p}
            onClick={() => update('keywords', [...data.keywords, p])}
            style={{ background: 'transparent', border: '1px dashed var(--border-strong)', color: 'var(--ink-muted)', padding: '4px 10px', borderRadius: 999, fontSize: 12, fontWeight: 500, cursor: 'pointer' }}
          >+ {p}</button>
        ))}
      </div>

      <Label style={{ marginTop: 28 }}>Ausschließen</Label>
      <div style={{ display: 'flex', flexWrap: 'wrap', gap: 6, marginBottom: 10 }}>
        {data.excludeKeywords.map(k => (
          <span key={k} className="chip chip-danger" style={{ paddingRight: 6 }}>
            – {k}
            <button onClick={() => toggle(k, data.excludeKeywords, 'excludeKeywords')} style={{
              background: 'transparent', border: 0, padding: 0, marginLeft: 4, cursor: 'pointer', display: 'flex',
            }}><I.x style={{ width: 14, height: 14, color: 'var(--danger)' }} /></button>
          </span>
        ))}
      </div>
      <Input
        value={exInput} onChange={setExInput}
        placeholder="Ausschluss eingeben + ↵"
        onKeyDown={e => {
          if (e.key === 'Enter' && exInput.trim()) {
            update('excludeKeywords', [...data.excludeKeywords, exInput.trim().toLowerCase()]);
            setExInput('');
          }
        }}
      />
      <div style={{ display: 'flex', flexWrap: 'wrap', gap: 6, marginTop: 8 }}>
        {exPresets.filter(p => !data.excludeKeywords.includes(p)).map(p => (
          <button key={p}
            onClick={() => update('excludeKeywords', [...data.excludeKeywords, p])}
            style={{ background: 'transparent', border: '1px dashed var(--border-strong)', color: 'var(--ink-muted)', padding: '4px 10px', borderRadius: 999, fontSize: 12, fontWeight: 500, cursor: 'pointer' }}
          >+ {p}</button>
        ))}
      </div>
    </div>
  );
}

function BuilderStep4({ data, update }) {
  const togglePlatform = (p) => {
    const set = new Set(data.platforms);
    if (set.has(p)) set.delete(p); else set.add(p);
    update('platforms', [...set]);
  };
  return (
    <div>
      <StepHeader
        overline="Quellen & KI"
        title="Wo & wie suchen?"
        subtitle="Plattformen und automatische KI-Bewertung."
      />
      <Label>Plattformen</Label>
      <div style={{ display: 'flex', flexDirection: 'column', gap: 8 }}>
        <PlatformOption
          name="ImmoScout24"
          desc="Großes Angebot, regelmäßige Updates"
          active={data.platforms.includes('immoscout24')}
          onToggle={() => togglePlatform('immoscout24')}
          color="#1F6B3A"
        />
        <PlatformOption
          name="Kleinanzeigen"
          desc="Oft provisionsfrei, kleinere Anbieter"
          active={data.platforms.includes('kleinanzeigen')}
          onToggle={() => togglePlatform('kleinanzeigen')}
          color="#C28428"
        />
      </div>

      {data.type === 'kauf' && (
        <>
          <Label style={{ marginTop: 24 }}>KI-Bewertung</Label>
          <div
            onClick={() => update('aiEnabled', !data.aiEnabled)}
            className="card" style={{ padding: 16, cursor: 'pointer' }}
          >
            <div style={{ display: 'flex', alignItems: 'flex-start', gap: 12 }}>
              <div style={{
                width: 40, height: 40, borderRadius: 12,
                background: data.aiEnabled ? 'var(--primary)' : 'var(--surface-2)',
                color: data.aiEnabled ? '#fff' : 'var(--ink-muted)',
                display: 'flex', alignItems: 'center', justifyContent: 'center',
                flexShrink: 0,
              }}>
                <I.spark />
              </div>
              <div style={{ flex: 1 }}>
                <div style={{ fontSize: 15, fontWeight: 700, color: 'var(--ink)' }}>Automatische KI-Analyse</div>
                <div style={{ fontSize: 12, color: 'var(--ink-muted)', marginTop: 4, lineHeight: 1.5 }}>
                  Jedes neue Inserat erhält einen Profitabilitäts-Score (0–100), inkl. Stärken, Risiken & Renditeschätzung.
                </div>
              </div>
              <Toggle on={data.aiEnabled} />
            </div>
          </div>
          {data.aiEnabled && (
            <p style={{ fontSize: 11, color: 'var(--ink-muted)', marginTop: 8, padding: '0 4px', lineHeight: 1.5 }}>
              Verbrauch: ca. 1 KI-Token pro Inserat. Bewertungen ≥ 80 erhalten Sie als Push-Mitteilung.
            </p>
          )}
        </>
      )}

      <div className="card" style={{ marginTop: 24, padding: 16, background: 'var(--surface-2)' }}>
        <div style={{ fontSize: 12, fontWeight: 700, color: 'var(--ink-muted)', textTransform: 'uppercase', letterSpacing: 0.05, marginBottom: 8 }}>
          Zusammenfassung
        </div>
        <div style={{ fontSize: 14, color: 'var(--ink)', lineHeight: 1.6 }}>
          {data.type === 'kauf' ? 'Kauf' : 'Miete'} in <strong>{data.city}</strong> +{data.radius}km<br/>
          <strong>{fmtPriceShort(data.priceMin)}–{fmtPriceShort(data.priceMax)}</strong>, {data.roomsMin}–{data.roomsMax} Zi., {data.areaMin}–{data.areaMax} m²<br/>
          {data.keywords.length > 0 && <>Stichwörter: {data.keywords.join(', ')}<br/></>}
          Plattformen: {data.platforms.length}
        </div>
      </div>
    </div>
  );
}

function PlatformOption({ name, desc, active, onToggle, color }) {
  return (
    <div onClick={onToggle} className="card" style={{ padding: 14, cursor: 'pointer', display: 'flex', alignItems: 'center', gap: 12 }}>
      <div style={{ width: 36, height: 36, borderRadius: 10, background: color + '20', color, display: 'flex', alignItems: 'center', justifyContent: 'center' }}>
        <I.globe />
      </div>
      <div style={{ flex: 1 }}>
        <div style={{ fontSize: 14, fontWeight: 700, color: 'var(--ink)' }}>{name}</div>
        <div style={{ fontSize: 12, color: 'var(--ink-muted)' }}>{desc}</div>
      </div>
      <div style={{
        width: 24, height: 24, borderRadius: 7, flexShrink: 0,
        background: active ? 'var(--ink)' : 'transparent',
        border: active ? '0' : '2px solid var(--border-strong)',
        display: 'flex', alignItems: 'center', justifyContent: 'center', color: '#fff',
      }}>{active && <I.check style={{ width: 16, height: 16 }} />}</div>
    </div>
  );
}

function Toggle({ on }) {
  return (
    <div style={{
      width: 44, height: 26, borderRadius: 999, flexShrink: 0,
      background: on ? 'var(--primary)' : 'var(--border-strong)',
      position: 'relative', transition: 'background .2s ease',
    }}>
      <div style={{
        position: 'absolute', top: 3, left: on ? 21 : 3,
        width: 20, height: 20, borderRadius: 999, background: '#fff',
        boxShadow: '0 1px 3px rgba(0,0,0,.2)', transition: 'left .2s ease',
      }} />
    </div>
  );
}

// ─── Form primitives ───────────────────────────────────────────────────
function Label({ children, style }) {
  return <div style={{ fontSize: 12, fontWeight: 700, color: 'var(--ink-muted)', textTransform: 'uppercase', letterSpacing: 0.04, marginBottom: 8, ...style }}>{children}</div>;
}
function Input({ value, onChange, placeholder, onKeyDown, type = 'text' }) {
  return (
    <input
      value={value} onChange={e => onChange(e.target.value)} placeholder={placeholder}
      type={type} onKeyDown={onKeyDown}
      style={{
        width: '100%', padding: '13px 14px', fontSize: 15, borderRadius: 12,
        background: 'var(--surface)', border: '1px solid var(--border)',
        fontFamily: 'var(--font-sans)', color: 'var(--ink)', outline: 'none',
        boxSizing: 'border-box',
      }}
    />
  );
}
function Pill({ children, active, onClick }) {
  return (
    <button onClick={onClick} style={{
      padding: '9px 14px', borderRadius: 999, border: 0, cursor: 'pointer',
      background: active ? 'var(--ink)' : 'var(--surface)',
      color: active ? '#fff' : 'var(--ink)',
      fontSize: 13, fontWeight: 600,
      boxShadow: active ? 'none' : 'inset 0 0 0 1px var(--border)',
    }}>{children}</button>
  );
}
function RangeRow({ min, max, onMin, onMax, fmt, absMin, absMax, step }) {
  return (
    <div>
      <div style={{ display: 'flex', justifyContent: 'space-between', fontSize: 16, fontWeight: 700, marginBottom: 10 }}>
        <span>{fmt(min)}</span>
        <span style={{ color: 'var(--ink-muted)' }}>—</span>
        <span>{fmt(max)}</span>
      </div>
      <div style={{ display: 'flex', gap: 8 }}>
        <input type="range" min={absMin} max={absMax} step={step} value={min}
          onChange={e => onMin(Math.min(+e.target.value, max))}
          style={{ flex: 1, accentColor: 'var(--primary)' }}
        />
        <input type="range" min={absMin} max={absMax} step={step} value={max}
          onChange={e => onMax(Math.max(+e.target.value, min))}
          style={{ flex: 1, accentColor: 'var(--primary)' }}
        />
      </div>
    </div>
  );
}

// ─── SEARCH RESULTS ────────────────────────────────────────────────────
function ResultsScreen({ ctx, searchId }) {
  const { listings, searches, navigate, back, favs, toggleFav, deleteSearch } = ctx;
  const search = searches.find(s => s.id === searchId) || searches[0];
  const [sort, setSort] = React.useState('score'); // score | price | newest
  const [view, setView] = React.useState('cards'); // cards | table
  const [filterOpen, setFilterOpen] = React.useState(false);
  const [filters, setFilters] = React.useState({
    platforms: { immoscout24: true, kleinanzeigen: true },
    minScore: 0,
    provFreeOnly: false,
  });
  const [refreshing, setRefreshing] = React.useState(false);

  // Apply filters
  let filtered = listings.filter(l => l.type === search.category);
  if (search.category === 'kauf') {
    filtered = filtered.filter(l => l.price >= search.priceMin && l.price <= search.priceMax);
  }
  filtered = filtered.filter(l => filters.platforms[l.platform]);
  if (filters.minScore > 0) filtered = filtered.filter(l => l.aiScore && l.aiScore >= filters.minScore);
  if (filters.provFreeOnly) filtered = filtered.filter(l => l.provisionsfrei);

  filtered = [...filtered].sort((a, b) => {
    if (sort === 'score') return (b.aiScore || 0) - (a.aiScore || 0);
    if (sort === 'price') return a.price - b.price;
    if (sort === 'newest') return new Date(b.posted) - new Date(a.posted);
    return 0;
  });

  const doRefresh = () => {
    setRefreshing(true);
    setTimeout(() => setRefreshing(false), 1400);
  };
  const doEvaluate = () => {
    alert('KI-Bewertung gestartet — ' + filtered.filter(l => !l.aiScore).length + ' Inserate werden analysiert. Sie erhalten eine Mitteilung wenn fertig.');
  };
  const doExport = () => {
    alert('CSV-Export wurde vorbereitet: ' + filtered.length + ' Zeilen.\n\n(Demo-Prototyp)');
  };
  const doDelete = () => {
    if (confirm(`Suche „${search.name}" wirklich löschen?`)) {
      deleteSearch(search.id);
      back();
    }
  };

  return (
    <div style={{ height: '100%', display: 'flex', flexDirection: 'column', background: 'var(--bg)' }}>
      <TopBar
        title={search.name}
        onBack={back}
        trailing={<>
          <IconBtn onClick={doRefresh}>
            <I.refresh style={{
              animation: refreshing ? 'spin .8s linear infinite' : 'none',
            }} />
          </IconBtn>
          <ResultsMoreMenu onExport={doExport} onEvaluate={doEvaluate} onDelete={doDelete} />
        </>}
      />
      <style>{`@keyframes spin { from { transform: rotate(0) } to { transform: rotate(360deg) } }`}</style>

      {/* Filter / sort bar */}
      <div style={{
        position: 'sticky', top: 'auto', zIndex: 10,
        padding: '4px 16px 12px', display: 'flex', gap: 8, alignItems: 'center',
        background: 'var(--bg)', borderBottom: '0.5px solid var(--border)',
        overflowX: 'auto',
      }} className="no-scrollbar">
        <button onClick={() => setFilterOpen(true)} className="chip" style={{ flexShrink: 0, padding: '7px 12px', background: 'var(--surface)', border: '1px solid var(--border)' }}>
          <I.filter style={{ width: 14, height: 14 }} /> Filter
          {(filters.minScore > 0 || filters.provFreeOnly) && (
            <span style={{ background: 'var(--primary)', color: '#fff', borderRadius: 999, fontSize: 9, padding: '1px 5px', marginLeft: 2 }}>•</span>
          )}
        </button>
        <SortPill active={sort === 'score'} onClick={() => setSort('score')}>KI-Score</SortPill>
        <SortPill active={sort === 'price'} onClick={() => setSort('price')}>Preis ↑</SortPill>
        <SortPill active={sort === 'newest'} onClick={() => setSort('newest')}>Neueste</SortPill>
        <div style={{ marginLeft: 'auto', display: 'flex', gap: 0, background: 'var(--surface)', borderRadius: 999, padding: 3, border: '1px solid var(--border)' }}>
          <ViewBtn active={view === 'cards'} onClick={() => setView('cards')}><I.grid style={{ width: 14, height: 14 }} /></ViewBtn>
          <ViewBtn active={view === 'table'} onClick={() => setView('table')}><I.list style={{ width: 14, height: 14 }} /></ViewBtn>
        </div>
      </div>

      <div className="phone-scroll" style={{ flex: 1, padding: '12px 16px 100px' }}>
        {/* Summary */}
        <div style={{ display: 'flex', justifyContent: 'space-between', alignItems: 'center', padding: '4px 4px 12px' }}>
          <div style={{ fontSize: 13, color: 'var(--ink-muted)' }}>
            <strong style={{ color: 'var(--ink)' }}>{filtered.length}</strong> Treffer · zuletzt aktualisiert {fmtRelative(search.lastRun)}
          </div>
          {search.newToday > 0 && <span className="chip chip-accent" style={{ fontSize: 10 }}>+{search.newToday} neu</span>}
        </div>

        {filtered.length === 0 ? (
          <EmptyState
            icon={<I.search />}
            title="Keine Treffer"
            subtitle="Lockern Sie die Filter oder fügen Sie weitere Plattformen hinzu."
            cta={<button onClick={() => setFilters({ platforms: { immoscout24: true, kleinanzeigen: true }, minScore: 0, provFreeOnly: false })} className="btn btn-outline">Filter zurücksetzen</button>}
          />
        ) : view === 'cards' ? (
          <div style={{ display: 'flex', flexDirection: 'column', gap: 14 }}>
            {filtered.map(l => (
              <ListingCard key={l.id} listing={l} onTap={() => navigate('listing', { id: l.id })} isFav={favs.has(l.id)} onFav={toggleFav} />
            ))}
          </div>
        ) : (
          <ResultsTable listings={filtered} navigate={navigate} favs={favs} toggleFav={toggleFav} />
        )}
      </div>

      {/* Filter sheet */}
      <Sheet open={filterOpen} onClose={() => setFilterOpen(false)} title="Filter" height="62%">
        <div style={{ padding: '4px 20px 24px' }}>
          <Label>Plattformen</Label>
          <div style={{ display: 'flex', gap: 8, marginBottom: 24 }}>
            <FilterToggleCard
              label="ImmoScout24" active={filters.platforms.immoscout24}
              onClick={() => setFilters(f => ({ ...f, platforms: { ...f.platforms, immoscout24: !f.platforms.immoscout24 } }))}
            />
            <FilterToggleCard
              label="Kleinanzeigen" active={filters.platforms.kleinanzeigen}
              onClick={() => setFilters(f => ({ ...f, platforms: { ...f.platforms, kleinanzeigen: !f.platforms.kleinanzeigen } }))}
            />
          </div>

          {search.category === 'kauf' && (
            <>
              <Label>Mindest-KI-Score: <strong>{filters.minScore || 'alle'}</strong></Label>
              <input
                type="range" min="0" max="90" step="10" value={filters.minScore}
                onChange={e => setFilters(f => ({ ...f, minScore: +e.target.value }))}
                style={{ width: '100%', accentColor: 'var(--primary)' }}
              />
              <div style={{ display: 'flex', justifyContent: 'space-between', fontSize: 11, color: 'var(--ink-muted)', marginTop: 2, marginBottom: 24 }}>
                <span>alle</span><span>50</span><span>80+</span>
              </div>
            </>
          )}

          <Label>Nur provisionsfrei</Label>
          <div onClick={() => setFilters(f => ({ ...f, provFreeOnly: !f.provFreeOnly }))} className="card" style={{ padding: 14, cursor: 'pointer', display: 'flex', alignItems: 'center', gap: 10 }}>
            <div style={{ flex: 1, fontSize: 14, fontWeight: 600 }}>Maklerprovision ausschließen</div>
            <Toggle on={filters.provFreeOnly} />
          </div>

          <button
            onClick={() => setFilterOpen(false)}
            className="btn btn-primary" style={{ width: '100%', marginTop: 24, padding: 14 }}
          >
            {filtered.length} Treffer anzeigen
          </button>
        </div>
      </Sheet>
    </div>
  );
}

function SortPill({ children, active, onClick }) {
  return (
    <button onClick={onClick} className="chip" style={{
      flexShrink: 0, padding: '7px 12px',
      background: active ? 'var(--ink)' : 'var(--surface)',
      color: active ? '#fff' : 'var(--ink)',
      border: active ? '1px solid var(--ink)' : '1px solid var(--border)',
    }}>{children}</button>
  );
}
function ViewBtn({ active, onClick, children }) {
  return (
    <button onClick={onClick} style={{
      border: 0, padding: '6px 10px', borderRadius: 999, cursor: 'pointer',
      background: active ? 'var(--ink)' : 'transparent',
      color: active ? '#fff' : 'var(--ink-muted)',
      display: 'flex', alignItems: 'center', gap: 4,
    }}>{children}</button>
  );
}
function FilterToggleCard({ label, active, onClick }) {
  return (
    <div onClick={onClick} style={{
      flex: 1, padding: '14px 12px', borderRadius: 12, cursor: 'pointer',
      background: active ? 'var(--ink)' : 'var(--surface)',
      color: active ? '#fff' : 'var(--ink)',
      border: active ? '0' : '1px solid var(--border)',
      fontSize: 13, fontWeight: 600, textAlign: 'center',
      display: 'flex', alignItems: 'center', justifyContent: 'center', gap: 6,
    }}>
      <span style={{ width: 8, height: 8, borderRadius: 999, background: active ? '#fff' : 'var(--border-strong)' }} />
      {label}
    </div>
  );
}
function ResultsMoreMenu({ onExport, onEvaluate, onDelete }) {
  const [open, setOpen] = React.useState(false);
  return (
    <div style={{ position: 'relative' }}>
      <IconBtn onClick={() => setOpen(!open)}><I.more /></IconBtn>
      {open && (
        <>
          <div onClick={() => setOpen(false)} style={{ position: 'fixed', inset: 0, zIndex: 50 }} />
          <div style={{
            position: 'absolute', top: 46, right: 0, zIndex: 60,
            background: 'var(--surface)', borderRadius: 14, padding: 6,
            boxShadow: 'var(--shadow-pop)', minWidth: 200,
            border: '1px solid var(--border)',
          }}>
            <MenuItem icon={<I.spark />} onClick={() => { setOpen(false); onEvaluate(); }}>KI-Bewertung starten</MenuItem>
            <MenuItem icon={<I.download />} onClick={() => { setOpen(false); onExport(); }}>Als CSV exportieren</MenuItem>
            <div style={{ height: 1, background: 'var(--border)', margin: '4px 6px' }} />
            <MenuItem icon={<I.trash />} danger onClick={() => { setOpen(false); onDelete(); }}>Suche löschen</MenuItem>
          </div>
        </>
      )}
    </div>
  );
}
function MenuItem({ icon, children, onClick, danger }) {
  return (
    <button onClick={onClick} style={{
      width: '100%', padding: '10px 12px', display: 'flex', alignItems: 'center', gap: 10,
      background: 'transparent', border: 0, cursor: 'pointer',
      color: danger ? 'var(--danger)' : 'var(--ink)',
      fontSize: 14, fontWeight: 500, borderRadius: 9, textAlign: 'left',
    }}>{icon}{children}</button>
  );
}

function ResultsTable({ listings, navigate, favs, toggleFav }) {
  return (
    <div className="card" style={{ overflow: 'hidden' }}>
      {listings.map((l, i) => (
        <div
          key={l.id} onClick={() => navigate('listing', { id: l.id })}
          style={{
            display: 'flex', gap: 12, padding: 12, alignItems: 'center', cursor: 'pointer',
            borderBottom: i < listings.length - 1 ? '0.5px solid var(--border)' : 'none',
          }}
        >
          <div className="photo" style={{ width: 64, height: 64, borderRadius: 10, backgroundImage: `url(${l.photos[0]})`, flexShrink: 0 }} />
          <div style={{ flex: 1, minWidth: 0 }}>
            <div style={{ fontSize: 14, fontWeight: 600, color: 'var(--ink)', overflow: 'hidden', textOverflow: 'ellipsis', whiteSpace: 'nowrap' }}>{l.title}</div>
            <div style={{ fontSize: 11, color: 'var(--ink-muted)', marginTop: 2 }}>
              {l.district} · {fmtArea(l.area)} · {l.rooms} Zi.
            </div>
            <div style={{ display: 'flex', alignItems: 'center', gap: 6, marginTop: 6 }}>
              <PlatformBadge platform={l.platform} />
              <span style={{ fontSize: 13, fontWeight: 700 }}>{fmtPriceShort(l.price)}</span>
            </div>
          </div>
          {l.aiScore && (
            <div style={{
              width: 32, height: 32, borderRadius: 999, color: '#fff', fontSize: 12, fontWeight: 800,
              background: l.aiScore >= 80 ? '#2F8F5A' : l.aiScore >= 60 ? '#C28428' : '#C8331C',
              display: 'flex', alignItems: 'center', justifyContent: 'center', flexShrink: 0,
            }}>{l.aiScore}</div>
          )}
        </div>
      ))}
    </div>
  );
}

Object.assign(window, { DashboardScreen, SearchBuilderScreen, ResultsScreen, IconBtn, Section, Toggle, Label });
