// app.jsx — main one-pager app. Uses window.Tacho, window.RedlineBar, useTweaks + Tweak* controls.
const { useState, useEffect, useRef, useCallback } = React;

/* ---------------- icons ---------------- */
const I = {
  arrow: <svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2.2"><path d="M5 12h14M13 6l6 6-6 6" /></svg>,
  mail: <svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.8"><rect x="3" y="5" width="18" height="14" rx="2" /><path d="m3 7 9 6 9-6" /></svg>,
  phone: <svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.8"><path d="M5 4h4l2 5-3 2a14 14 0 0 0 6 6l2-3 5 2v4a2 2 0 0 1-2 2A17 17 0 0 1 3 6a2 2 0 0 1 2-2" /></svg>,
  link: <svg viewBox="0 0 24 24" fill="currentColor"><path d="M4.98 3.5a2.5 2.5 0 1 0 0 5 2.5 2.5 0 0 0 0-5M3 9h4v12H3zM9 9h3.8v1.7h.05c.53-1 1.83-2 3.76-2C20.3 8.7 21 11 21 14.2V21h-4v-6c0-1.4 0-3.3-2-3.3s-2.3 1.5-2.3 3.2V21H9z" /></svg>,
  play: <svg viewBox="0 0 24 24" fill="currentColor"><path d="M6 4l14 8-14 8z" /></svg>,
  expand: <svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2"><path d="M9 3H3v6M21 9V3h-6M3 15v6h6M15 21h6v-6" /></svg>,
  close: <svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2.2"><path d="M6 6l12 12M18 6L6 18" /></svg>,
  award: <svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.8"><circle cx="12" cy="9" r="6" /><path d="M9 14l-2 7 5-3 5 3-2-7" /></svg>,
  doc: <svg viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="1.8"><path d="M14 3H7a2 2 0 0 0-2 2v14a2 2 0 0 0 2 2h10a2 2 0 0 0 2-2V8z" /><path d="M14 3v5h5M12 18v-6m0 6-2.5-2.5M12 18l2.5-2.5" /></svg>
};

/* ---------------- data ---------------- */
const EQUIP = [
{ name: "Markenstrategie", rpm: 7400, desc: "Ich gebe Marken eine klare Richtung — unverwechselbar positioniert und tragfähig über Jahre." },
{ name: "Integrierte Kommunikation", rpm: 7100, desc: "Ich orchestriere alle Kanäle zu einer Stimme, die über jeden Touchpoint konsequent wirkt." },
{ name: "Digital Marketing", rpm: 6800, desc: "Ich verbinde Daten, Content und Performance zu Kampagnen, die messbar Resultate liefern." },
{ name: "Konzept & Text", rpm: 7600, desc: "Ich schreibe Texte, die ankommen. Und Wirkung zeigen. Mal Fortissimo, mal Pianissimo. Genauso, wie es die Zielgruppe braucht." }];

const PROJECTS = [
{ kunde: "Weltbild Schweiz", branche: "Verlag", aufgabe: "Ausarbeitung einer crossmedialen Testimonial-Kampagne für Weltbild, um neue Kundensegmente zu erschliessen.", ergebnis: "Mit Stefanie Heinzmann als Markenbotschafterin konnte Weltbild Schweiz eine jüngere Zielgruppe ansprechen. Die Walliser Pop- und Soulinterpretin verfügt über einen hohen Wiedererkennungswert und verkörpert gleichermassen Bodenständigkeit wie einen modernen Zeitgeist — Werte, die sich auch Weltbild auf die Fahne geschrieben hat. Ebenso konnte der Website-Traffic signifikant gesteigert und die Zahl der Follower auf den sozialen Medien ausgebaut werden." },
{ kunde: "Advery", branche: "Werbeagentur / Kommunikation", aufgabe: "Strategische und operative Führung der Kommunikationsagentur Advery — von Positionierung und New Business über Kundenakquisition bis zur Team- und Talententwicklung.", ergebnis: "Aus der Agentur eines sozialintegrativen Ausbildungsbetriebs wurde ein Anbieter, der sich auch bei Kunden ohne sozialen Bezug behauptete — anerkannt für Qualität statt Wohltätigkeit, konkurrenzfähig in der Region und mit gestärkter Auftragslage." },
{ kunde: "OPO Oeschger", branche: "Holzhandel / Beschläge", aufgabe: "Marktbearbeitung in der Schweiz und Deutschland, analog und digital — von der Messekonzeption über die Erneuerung sämtlicher Werbemittel bis zur Betreuung des Kundenmagazins und Erschliessung neuer Absatzkanäle.", ergebnis: "Ausbau der Marktpräsenz des Familienunternehmens: Messeauftritte optimiert, Kundenbindung verstärkt und durch die Mitausrichterschaft am Bundesgestaltungswettbewerb «Die Gute Form» (Tischler Schreiner Deutschland) Zugang zu neuen Schreinerei-Adressen für gezielte Angebote erhalten." }];


/* ---------------- scroll helpers ---------------- */
function scrollToId(id) {
  const el = document.getElementById(id);
  if (el) {const y = el.getBoundingClientRect().top + window.scrollY - 58;window.scrollTo({ top: y, behavior: 'smooth' });}
}
function useReveal(dep) {
  useEffect(() => {
    const els = [...document.querySelectorAll('.reveal:not(.in)')];
    const io = new IntersectionObserver((es) => {
      es.forEach((e) => {if (e.isIntersecting) {e.target.classList.add('in');io.unobserve(e.target);}});
    }, { threshold: .14, rootMargin: '0px 0px -8% 0px' });
    els.forEach((el) => io.observe(el));
    return () => io.disconnect();
  }, [dep]);
}

/* ---------------- Nav ---------------- */
function Nav({ vocab }) {
  const [show, setShow] = useState(false);
  const [open, setOpen] = useState(false);
  const [active, setActive] = useState('hero');
  const links = [
  { id: 'fahrer', label: vocab ? 'Der Fahrer' : 'Über mich' },
  { id: 'ausstattung', label: vocab ? 'Ausstattung' : 'Leistungen' },
  { id: 'serviceheft', label: vocab ? 'Serviceheft' : 'Referenzen' }];

  useEffect(() => {
    const onScroll = () => setShow(window.scrollY > window.innerHeight * 0.62);
    onScroll();window.addEventListener('scroll', onScroll, { passive: true });
    return () => window.removeEventListener('scroll', onScroll);
  }, []);
  useEffect(() => {
    const ids = ['hero', ...links.map((l) => l.id)];
    const io = new IntersectionObserver((es) => {
      es.forEach((e) => {if (e.isIntersecting) setActive(e.target.id);});
    }, { rootMargin: '-45% 0px -50% 0px' });
    ids.forEach((id) => {const el = document.getElementById(id);if (el) io.observe(el);});
    return () => io.disconnect();
  }, [vocab]);
  const go = (id) => {setOpen(false);scrollToId(id);};
  return (
    <nav className={'nav' + (show ? ' show' : '') + (open ? ' open' : '')}>
      <div className="nav-brand" onClick={() => {setOpen(false);window.scrollTo({ top: 0, behavior: 'smooth' });}}>
        <span className="dot"></span>M. SCHÖNHOLZER
      </div>
      <ul className="nav-links">
        {links.map((l) =>
        <li key={l.id}><a className={active === l.id ? 'active' : ''} onClick={() => go(l.id)}>{l.label}</a></li>
        )}
        <li><a className="nav-cta" onClick={() => go('kontakt')}>{vocab ? 'Probefahrt' : 'Kontakt aufnehmen'}</a></li>
      </ul>
      <button className="nav-burger" aria-label="Menü" onClick={() => setOpen((o) => !o)}>
        <svg width="26" height="26" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2"><path d={open ? 'M6 6l12 12M6 18L18 6' : 'M4 7h16M4 12h16M4 17h16'} /></svg>
      </button>
    </nav>);

}

/* ---------------- Hero ---------------- */
function Hero({ variant, vocab, anim }) {
  const Name =
  <h1 className="hero-name"><span className="ln1">MARK</span><br /><span className="ln2">SCHÖNHOLZER</span></h1>;

  const role = <div className="hero-role">Senior Marketing Leader &amp; Senior-Texter · Zürich</div>;
  const tag = <p className="hero-tag">40 Jahre Kommunikation. <b>Der Motor läuft auf Hochtouren.</b></p>;
  const cta =
  <div className="hero-cta">
      <button className="btn btn--primary" onClick={() => scrollToId('kontakt')}>Kontakt aufnehmen {I.arrow}</button>
      <button className="btn btn--ghost" onClick={() => scrollToId('fahrer')}>Mehr erfahren</button>
    </div>;


  let inner;
  if (variant === 'split') {
    inner =
    <div className="hero-split-grid">
        <div>{role}{Name}{tag}{cta}</div>
        <div><Tacho target={7900} animate={anim} size={410} /></div>
      </div>;

  } else if (variant === 'redline') {
    inner =
    <div style={{ maxWidth: 860, margin: '0 auto', textAlign: 'center' }}>
        {role}{Name}
        <div className="redline-wrap"><RedlineBar target={7900} animate={anim} /></div>
        {tag}
        <div style={{ display: 'flex', justifyContent: 'center' }}>{cta}</div>
      </div>;

  } else {// vollgas
    inner =
    <div style={{ textAlign: 'center' }}>
        <Tacho target={7900} animate={anim} size={440} />
        {Name}{role}{tag}
        {cta}
      </div>;

  }
  return (
    <section id="hero" className={'hero hero-' + variant}>
      <div className="hero-bg"></div>
      <div className="hero-grid-tex"></div>
      <div className="wrap">{inner}</div>
      <div className="scroll-hint">SCROLLEN<span className="arr"></span></div>
    </section>);

}

/* ---------------- Der Fahrer ---------------- */
function Fahrer({ vocab }) {
  return (
    <section id="fahrer" className="section-pad section--light">
      <div className="wrap">
        <div className="reveal">
          <div className="eyebrow">{vocab ? 'Über mich' : 'Der Fahrer'}</div>
          <h2 className="sec-title">{vocab ? 'Der Fahrer' : 'Über mich'}</h2>
        </div>
        <div className="fahrer-grid">
          <div className="fahrer-photo-wrap reveal">
            <div className="fahrer-photo-inner">
              <div className="fahrer-photo">
                <img src="assets/mark-portrait.png" alt="Porträt von Mark Schönholzer" className="fahrer-portrait" />
              </div>
              <div className="photo-badge"><span className="dot" style={{ width: 8, height: 8, borderRadius: '50%', background: '#fff' }}></span>MARK SCHÖNHOLZER</div>
            </div>
            <a className="btn btn--primary fahrer-cv" href={window.__resources && window.__resources.cv || "CV-Mark-Schoenholzer.pdf"} download="CV-Mark-Schoenholzer.pdf" target="_blank" rel="noopener">{I.doc} CV als PDF herunterladen</a>
          </div>
          <div className="fahrer-text reveal">
            <p>Ich mache Marketing aus Überzeugung. Und nicht, weil ich es gelernt habe. Ich verbinde Strategie, Konzept und Kreation zu Ideen, die Relevanz haben und Wirkung zeigen.</p>
            <p>Ich setze um, halte die Fäden zusammen und bewahre einen kühlen Kopf, auch wenn die Hütte brennt. Mit 40 Jahren Erfahrung über Agenturen, Verlage und KMUs hinweg weiss ich, wie Marketing in der Praxis funktioniert. Und nicht nur auf dem Papier.</p>
            <div className="driver-quote">«ICH ARBEITE MIT KOPF, HERZ UND MANCHMAL AUCH BAUCH.»</div>
            <div className="driver-spec">
              <div className="it"><span className="num">40</span><span className="lab">Jahre im Marketing</span></div>
              <div className="it"><span className="num">3</span><span className="lab">Welten: Agentur · Verlag · KMU</span></div>
              <div className="it"><span className="num">2×</span><span className="lab">Bronze · Dialogmarketing-Preis</span></div>
            </div>
          </div>
        </div>
      </div>
    </section>);

}

/* ---------------- Ausstattung (RPM bars) ---------------- */
function EquipRow({ item, idx, anim }) {
  const fillRef = useRef(null);
  const rowRef = useRef(null);
  useEffect(() => {
    const fill = fillRef.current,row = rowRef.current;
    if (!fill || !row) return;
    if (!anim) {fill.style.width = '100%';return;}
    fill.style.width = '0%';
    let raf,started = false;
    const runFill = () => {
      if (started) return;started = true;
      const dur = 1100,delay = idx * 140;
      const ease = (p) => 1 - Math.pow(1 - p, 3);
      let t0 = null;
      const step = (now) => {
        if (t0 === null) t0 = now;
        const el = now - t0 - delay;
        if (el < 0) {raf = requestAnimationFrame(step);return;}
        const p = Math.min(el / dur, 1);
        fill.style.width = (ease(p) * 100).toFixed(2) + '%';
        if (p < 1) raf = requestAnimationFrame(step);
      };
      raf = requestAnimationFrame(step);
    };
    const check = () => {
      const r = row.getBoundingClientRect();
      const vh = window.innerHeight || document.documentElement.clientHeight;
      if (r.top < vh * 0.82 && r.bottom > 0) {runFill();cleanup();}
    };
    const cleanup = () => window.removeEventListener('scroll', check);
    window.addEventListener('scroll', check, { passive: true });
    check();
    return () => {cancelAnimationFrame(raf);cleanup();};
  }, [anim, idx]);
  return (
    <div className="equip-row reveal" ref={rowRef}>
      <div className="equip-name">{item.name}</div>
      <div className="equip-right">
        <div className="desc">{item.desc}</div>
        <div className="rpm-meter">
          <div className="rpm-track">
            <div className="rpm-fill" ref={fillRef}></div>
            <div className="rpm-redzone"></div>
          </div>
        </div>
      </div>
    </div>);

}
function Ausstattung({ vocab, anim }) {
  return (
    <section id="ausstattung" className="section-pad">
      <div className="wrap">
        <div className="reveal">
          <div className="eyebrow">{vocab ? 'Was ich biete' : 'Ausstattung'}</div>
          <h2 className="sec-title">{vocab ? 'Ausstattung' : 'Was ich biete'}</h2>
          <div className="sec-sub">Vier Leistungsfelder · serienmässig</div>
        </div>
        <div className="equip-list">
          {EQUIP.map((it, i) => <EquipRow key={it.name} item={it} idx={i} anim={anim} />)}
        </div>
      </div>
    </section>);

}

/* ---------------- Serviceheft ---------------- */
function Serviceheft({ vocab }) {
  const [zoom, setZoom] = useState(false);
  useEffect(() => {
    const onKey = (e) => {if (e.key === 'Escape') setZoom(false);};
    if (zoom) {document.body.style.overflow = 'hidden';window.addEventListener('keydown', onKey);}
    return () => {document.body.style.overflow = '';window.removeEventListener('keydown', onKey);};
  }, [zoom]);
  return (
    <section id="serviceheft" className="section-pad section--alt">
      <div className="wrap">
        <div className="reveal">
          <div className="eyebrow">{vocab ? 'Referenzen & Projekte' : 'Serviceheft'}</div>
          <h2 className="sec-title">{vocab ? 'Serviceheft' : 'Referenzen'}</h2>
          <div className="sec-sub">WAS AUF DEM WEG ZÄHLT:ERGEBNISSE, NICHT NUR NAMEN</div>
        </div>

        <div className="award reveal">
          <div className="award-badge"><span className="award-medal">BRONZE</span>{I.award}</div>
          <div className="award-txt">
            <div className="award-tag">Auszeichnung & Jury</div>
            <h3>Schweizer Dialogmarketing-Preis</h3>
            <ul className="award-creds">
              <li>
                <span className="ac-role">Bronze-Gewinner</span>
                <span className="ac-detail">National Geographic <em>(Anzeige)</em> · EasyJet <em>(E-Mailing)</em></span>
              </li>
              <li>
                <span className="ac-role">Unabhängiges Jurymitglied</span>
                <span className="ac-detail">Bewertung eingereichter Dialogmarketing-Arbeiten</span>
              </li>
            </ul>
          </div>
        </div>

        <div className="proj-list">
          {PROJECTS.map((p, i) =>
          <div className="proj-case reveal" key={i}>
              <div className="proj-case-head">
                <div className="proj-no">CASE {String(i + 1).padStart(2, '0')}</div>
                <div className="proj-kunde">{p.kunde}</div>
                <div className="proj-branche">{p.branche}</div>
              </div>
              <div className="proj-case-body">
                <div className="proj-field"><div className="k">Aufgabe</div><div className="v">{p.aufgabe}</div></div>
                <div className="proj-field"><div className="k">Ergebnis</div><div className="v">{p.ergebnis}</div></div>
              </div>
            </div>
          )}
        </div>

        <div className="video-block reveal">
          <div className="video-frame">
            <iframe className="video-embed" src="Mark Schoenholzer Video.html" loading="lazy"
            title="Mark Schönholzer — Für Branding mit Emotionen (animierter Markenfilm)"
            allow="autoplay"></iframe>
            <button className="video-expand" onClick={() => setZoom(true)} aria-label="Film im Vollbild ansehen">
              {I.expand}<span>Vergrössern</span>
            </button>
          </div>
          <div className="video-side">
            <h3>Für Branding mit Emotionen</h3>
            <p>Mal laut, mal leise, mal kraftvoll, mal ruhiger. Gute Kommunikation trifft den richtigen Ton.</p>
            <button className="btn btn--ghost video-play-big" onClick={() => setZoom(true)}>{I.play} Film abspielen</button>
          </div>
        </div>
        {zoom &&
        <div className="video-lightbox" onClick={() => setZoom(false)}>
          <button className="video-close" onClick={() => setZoom(false)} aria-label="Schliessen">{I.close}</button>
          <div className="video-lightbox-stage" onClick={(e) => e.stopPropagation()}>
            <iframe className="video-embed" src="Mark Schoenholzer Video.html"
            title="Mark Schönholzer — Für Branding mit Emotionen (animierter Markenfilm)"
            allow="autoplay"></iframe>
          </div>
        </div>}
      </div>
    </section>);

}

/* ---------------- Kontakt ---------------- */
function Kontakt({ vocab }) {
  return (
    <section id="kontakt" className="section-pad kontakt">
      <div className="wrap">
        <div className="reveal">
          <div className="eyebrow" style={{ justifyContent: 'center' }}>{vocab ? 'Lust auf eine Probefahrt?' : 'Kontakt'}</div>
          <h2 className="kontakt-line">Lassen Sie uns gemeinsam <span className="hl">Vollgas geben.</span></h2>
        </div>
        <div className="kontakt-cards reveal">
          <a className="kc" href="mailto:markschonholzer@gmail.com">
            <span className="ic">{I.mail}</span><span className="kl">E-Mail</span><span className="kv">markschonholzer@gmail.com</span>
          </a>
          <a className="kc" href="tel:+41794029072">
            <span className="ic">{I.phone}</span><span className="kl">Telefon</span><span className="kv">079 402 90 72</span>
          </a>
          <a className="kc" href="https://www.linkedin.com/in/markschoenholzer/" target="_blank" rel="noopener">
            <span className="ic">{I.link}</span><span className="kl">LinkedIn</span><span className="kv">/in/markschoenholzer</span>
          </a>
        </div>
        <div className="kontakt-foot reveal">
          <a className="btn btn--primary" href={window.__resources && window.__resources.cv || "CV-Mark-Schoenholzer.pdf"} download="CV-Mark-Schoenholzer.pdf" target="_blank" rel="noopener">{I.doc} CV als PDF herunterladen</a>
          <div className="footer" style={{ width: '100%' }}>
            <span className="dom">markschoenholzer.ch</span> &nbsp;·&nbsp; © {new Date().getFullYear()} Mark Schönholzer &nbsp;·&nbsp; Zürich
          </div>
        </div>
      </div>
    </section>);

}

/* ---------------- Tweaks ---------------- */
const TWEAK_DEFAULTS = /*EDITMODE-BEGIN*/{
  "heroVariant": "vollgas",
  "accent": "#C0392B",
  "motorVocab": true,
  "animations": true,
  "bodyFont": "Trebuchet MS"
} /*EDITMODE-END*/;

function App() {
  const [t, setTweak] = useTweaks(TWEAK_DEFAULTS);
  const vocab = t.motorVocab;
  const anim = t.animations;

  useEffect(() => {
    document.documentElement.style.setProperty('--accent', t.accent);
    document.documentElement.style.setProperty('--font-body', `'${t.bodyFont}','Barlow',system-ui,sans-serif`);
    document.documentElement.setAttribute('data-anim', anim ? 'on' : 'off');
    document.documentElement.setAttribute('data-reveal', anim ? 'on' : 'off');
  }, [t.accent, t.bodyFont, anim]);

  useReveal('' + vocab + anim + t.heroVariant);

  return (
    <React.Fragment>
      <Nav vocab={vocab} />
      <Hero variant={t.heroVariant} vocab={vocab} anim={anim} key={t.heroVariant + anim} />
      <Fahrer vocab={vocab} />
      <Ausstattung vocab={vocab} anim={anim} />
      <Serviceheft vocab={vocab} />
      <Kontakt vocab={vocab} />

      <TweaksPanel>
        <TweakSection label="Startseite" />
        <TweakRadio label="Hero-Variante" value={t.heroVariant}
        options={['vollgas', 'split', 'redline']}
        onChange={(v) => setTweak('heroVariant', v)} />
        <TweakSection label="Marke" />
        <TweakColor label="Akzentfarbe" value={t.accent}
        options={['#C0392B', '#D35400', '#A6271B', '#D81E2C']}
        onChange={(v) => setTweak('accent', v)} />
        <TweakRadio label="Schrift (Fliesstext)" value={t.bodyFont}
        options={['Trebuchet MS', 'Barlow']}
        onChange={(v) => setTweak('bodyFont', v)} />
        <TweakSection label="Inhalt & Motion" />
        <TweakToggle label="Motor-Vokabular" value={t.motorVocab}
        onChange={(v) => setTweak('motorVocab', v)} />
        <TweakToggle label="Animationen" value={t.animations}
        onChange={(v) => setTweak('animations', v)} />
      </TweaksPanel>
    </React.Fragment>);

}

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