/* css/surfer.css
   Cluster Surfer: Surfer auf der überrollenden Welle, nach dem Mockup.
   Die Pfade in index.html (.surfer) sind aus den Mockups nachgezeichnet
   (Potrace): der Surfer in neun Farbebenen, die Welle in sechs. Hier werden
   sie gefärbt und bewegt. Aufbau von unten nach oben: Wasser (dunkle
   Wellenwand, Brettschatten), Brett, Schaum, Strömung und Gischt, Körper.
   Animiert werden nur transform und opacity; Pausieren außerhalb des
   Viewports regelt js/surfer.js über .is-paused. Klassen mit Präfix .surfer-. */

.surfer-deep        { fill: #5b9da1; }
.surfer-board       { fill: #4d7f81; }
/* Welle (Aufgabe 76): sechs Töne von der dunklen Wand bis zum weißen Kamm */
.surfer-wave-dark   { fill: #78adb2; }
.surfer-wave-wall   { fill: #93c0c3; }
.surfer-wave-band   { fill: #abced0; }
.surfer-wave-mid    { fill: #bcdcdf; }
.surfer-wave-light  { fill: #d4e8ea; }
.surfer-wave-foam   { fill: #f8fdfd; }
.surfer-skin        { fill: #d39e7d; }
.surfer-skin-shade  { fill: #b47565; }
.surfer-shorts      { fill: #fa3c4a; }
.surfer-shorts-shade { fill: #d3444b; }
.surfer-hair        { fill: #282536; }


/* Animation (Aufgabe 65, Welle Aufgabe 76): Die Welle steht, das Wasser
   läuft hindurch. Die Wellenebenen bewegen sich deshalb nur minimal (Wand
   atmet, Kamm hebt sich leicht); die Strömung tragen die Partikel weiter
   unten. Der Surfer hält die Balance. Die Maße sind Einheiten des Mockups
   (ca. 0,5 px am Bildschirm). fill-box legt den Drehpunkt auf die jeweilige
   Form; der Körper dreht sich um die Füße (unten Mitte), damit sie auf dem
   Brett bleiben. */
.surfer-wave-dark,
.surfer-wave-wall,
.surfer-wave-foam,
.surfer-deep,
.surfer-board,
.surfer-body {
    transform-box: fill-box;
    transform-origin: 50% 50%;
}

.surfer-body {
    transform-origin: 50% 100%;
    animation:
        surfer-body-sway 4.4s ease-in-out infinite,
        surfer-pendulum var(--pendulum) ease-in-out infinite;
}

/* Brett und Körper teilen dieselbe Hubbewegung (gleiche Dauer und Phase),
   damit die Füße nicht vom Brett abheben. */
.surfer-board {
    animation:
        surfer-board-sway 4.4s ease-in-out infinite,
        surfer-pendulum var(--pendulum) ease-in-out infinite;
}

.surfer-wave-dark,
.surfer-wave-wall {
    transform-origin: 50% 100%;
    animation: surfer-wave-swell 8s ease-in-out infinite;
}

.surfer-wave-foam {
    animation: surfer-wave-crest 5.2s ease-in-out infinite;
}

.surfer-deep {
    animation:
        surfer-shadow-drift 4.4s ease-in-out -1.1s infinite,
        surfer-pendulum var(--pendulum) ease-in-out infinite;
}

@keyframes surfer-body-sway {
    0%,
    100% { transform: translate(0, 0) rotate(-0.9deg); }
    50% { transform: translate(1.5px, -3px) rotate(1deg); }
}

@keyframes surfer-board-sway {
    0%,
    100% { transform: translate(0, 0) rotate(-0.4deg); }
    50% { transform: translate(1.5px, -3px) rotate(0.4deg); }
}

@keyframes surfer-wave-swell {
    0%,
    100% { transform: scale(1, 1); }
    50% { transform: scale(1.004, 1.014); }
}

@keyframes surfer-wave-crest {
    0%,
    100% { transform: translate(0, 0); }
    50% { transform: translate(1.5px, -1.5px); }
}

@keyframes surfer-shadow-drift {
    0%,
    100% { transform: translate(0, 0) scale(1); opacity: 1; }
    50% { transform: translate(3px, 1px) scale(1.04, 1.1); opacity: 0.9; }
}

/* Pendeln zur Welle (Aufgabe 78): Damit Welle und Surfer nicht zu starr
   zusammenhängen, wandert die Figur kontinuierlich und leicht auf die Welle
   zu und wieder zurück (±12 Einheiten, ca. ±6 px, Takt 7 s). Es pendeln
   Körper, Brett, Brettschatten, Ringe/Bugwelle und Heckwelle gemeinsam
   (gleicher Takt und Start); die Welle bleibt stehen. Die Bewegung nutzt die
   einzelne Eigenschaft translate und läuft deshalb zusätzlich zum Wippen
   (transform). Sie wirkt im lokalen Koordinatensystem der Figur: Nach dem
   Umklappen (scaleX in .surfer-travel) zeigt sie weiter zur Welle. */
.surfer {
    --pendulum: 7s;
}

.surfer-wake,
.surfer-stern {
    animation: surfer-pendulum var(--pendulum) ease-in-out infinite;
}

@keyframes surfer-pendulum {
    0%,
    100% { translate: 12px 0; }
    50% { translate: -12px 0; }
}

/* Verdrängtes Wasser (Aufgabe 66): Das Brett schiebt das Wasser zur
   Seite. Drei versetzte Wellenringe laufen vom Brett nach außen und
   verblassen, zwei kurze Heckwellen ziehen am Brettende ab. Im Ruhezustand
   sind sie unsichtbar (opacity 0); sie liegen unter dem Brett. Die Ringe
   dehnen sich in der Höhe stärker als in der Länge, weil das Brett schmal
   ist. Dauer wie Wippen von Körper und Brett (4,4 s), damit der Rhythmus
   zusammenpasst. */
.surfer-ring,
.surfer-trail {
    fill: none;
    stroke: #d4ebea;
    stroke-linecap: round;
    opacity: 0;
    transform-box: fill-box;
}

.surfer-ring {
    stroke-width: 2.2;
    transform-origin: 50% 50%;
    animation: surfer-ring-spread 4.4s ease-out infinite;
}

.surfer-ring--2 { animation-delay: -1.47s; }
.surfer-ring--3 { animation-delay: -2.93s; }

.surfer-trail {
    stroke-width: 2;
    transform-origin: 0% 50%;
    animation: surfer-trail-fade 4.4s ease-out infinite;
}

.surfer-trail--2 { animation-delay: -2.2s; }

@keyframes surfer-ring-spread {
    0% { opacity: 0; transform: scale(1); }
    15% { opacity: 0.6; }
    100% { opacity: 0; transform: scale(1.5, 2.1); }
}

@keyframes surfer-trail-fade {
    0% { opacity: 0; transform: translate(0, 0) scaleX(0.7); }
    20% { opacity: 0.5; }
    100% { opacity: 0; transform: translate(10px, 0) scaleX(1.15); }
}

/* Strömendes Wellenwasser (Aufgaben 68, 76): Das Wasser läuft im
   Uhrzeigersinn durch die Welle: vom Brett am Boden nach links, die Wand
   hinauf, über den Kamm nach rechts und fällt an der Lippe ab. Drei Bahnen
   (a außen, b Mitte, c innen) führen kurze, in Laufrichtung gedrehte
   Striche entlang der Wellenform; jede Bahn hat vier Striche, abwechselnd
   hell (auf der dunklen Wand sichtbar) und dunkel (auf dem weißen Kamm
   sichtbar). Die Bahnen sind aus der Wellenform berechnet (Keyframes unten,
   Einheiten des Mockups) und mit clip-path (surfer-wave-clip) auf die Welle
   beschränkt. Gleichmäßige Geschwindigkeit (linear), die Verzögerung steht
   als Variable im HTML. */
.surfer-particle {
    fill: none;
    stroke: #f2fbfb;
    stroke-width: 2.8;
    stroke-linecap: round;
    opacity: 0;
    animation-duration: 7s;
    animation-timing-function: linear;
    animation-iteration-count: infinite;
    animation-delay: var(--p-delay, 0s);
}

.surfer-particle--dark {
    stroke: #5f9ba0;
}

.surfer-particle--a { animation-name: surfer-lane-a; }
.surfer-particle--b { animation-name: surfer-lane-b; }
.surfer-particle--c { animation-name: surfer-lane-c; }

@keyframes surfer-lane-a {
    0.0% { transform: translate(453.3px, 979.0px) rotate(-154deg); opacity: 0; }
    5.9% { transform: translate(424.3px, 964.6px) rotate(-152deg); opacity: 0.7; }
    11.8% { transform: translate(396.0px, 948.9px) rotate(-153deg); }
    17.6% { transform: translate(366.8px, 934.8px) rotate(-158deg); }
    23.5% { transform: translate(336.1px, 924.4px) rotate(-165deg); }
    29.4% { transform: translate(304.3px, 918.3px) rotate(-169deg); }
    35.3% { transform: translate(272.6px, 911.8px) rotate(-162deg); }
    41.2% { transform: translate(243.6px, 898.1px) rotate(-140deg); }
    47.1% { transform: translate(225.3px, 871.8px) rotate(-110deg); }
    52.9% { transform: translate(223.0px, 839.9px) rotate(-79deg); }
    58.8% { transform: translate(237.6px, 811.4px) rotate(-52deg); }
    64.7% { transform: translate(261.9px, 790.0px) rotate(-36deg); }
    70.6% { transform: translate(289.8px, 773.6px) rotate(-24deg); }
    76.5% { transform: translate(320.6px, 763.9px) rotate(-11deg); }
    82.4% { transform: translate(352.8px, 761.1px) rotate(4deg); }
    88.2% { transform: translate(384.4px, 767.9px) rotate(21deg); }
    94.1% { transform: translate(412.3px, 783.9px) rotate(45deg); opacity: 0.7; }
    100.0% { transform: translate(428.3px, 811.7px) rotate(60deg); opacity: 0; }
}

@keyframes surfer-lane-b {
    0.0% { transform: translate(470.0px, 993.3px) rotate(-154deg); opacity: 0; }
    5.9% { transform: translate(444.5px, 980.7px) rotate(-153deg); opacity: 0.7; }
    11.8% { transform: translate(419.3px, 967.7px) rotate(-152deg); }
    17.6% { transform: translate(394.3px, 954.1px) rotate(-152deg); }
    23.5% { transform: translate(369.3px, 940.6px) rotate(-152deg); }
    29.4% { transform: translate(344.3px, 927.1px) rotate(-152deg); }
    35.3% { transform: translate(319.2px, 913.8px) rotate(-150deg); }
    41.2% { transform: translate(295.4px, 898.3px) rotate(-142deg); }
    47.1% { transform: translate(274.8px, 878.9px) rotate(-127deg); }
    52.9% { transform: translate(262.0px, 853.8px) rotate(-102deg); }
    58.8% { transform: translate(263.6px, 825.9px) rotate(-71deg); }
    64.7% { transform: translate(279.2px, 802.4px) rotate(-46deg); }
    70.6% { transform: translate(302.0px, 785.7px) rotate(-27deg); }
    76.5% { transform: translate(329.0px, 777.1px) rotate(-8deg); }
    82.4% { transform: translate(357.3px, 778.0px) rotate(10deg); }
    88.2% { transform: translate(384.3px, 786.5px) rotate(26deg); }
    94.1% { transform: translate(407.3px, 802.8px) rotate(43deg); opacity: 0.7; }
    100.0% { transform: translate(425.0px, 825.0px) rotate(52deg); opacity: 0; }
}

@keyframes surfer-lane-c {
    0.0% { transform: translate(480.7px, 1002.3px) rotate(-155deg); opacity: 0; }
    5.9% { transform: translate(459.1px, 992.4px) rotate(-155deg); opacity: 0.7; }
    11.8% { transform: translate(437.8px, 982.0px) rotate(-153deg); }
    17.6% { transform: translate(416.8px, 971.0px) rotate(-151deg); }
    23.5% { transform: translate(396.1px, 959.3px) rotate(-150deg); }
    29.4% { transform: translate(375.7px, 947.2px) rotate(-147deg); }
    35.3% { transform: translate(356.4px, 933.4px) rotate(-140deg); }
    41.2% { transform: translate(339.3px, 917.0px) rotate(-131deg); }
    47.1% { transform: translate(325.4px, 897.9px) rotate(-120deg); }
    52.9% { transform: translate(315.5px, 876.3px) rotate(-110deg); }
    58.8% { transform: translate(309.3px, 853.5px) rotate(-98deg); }
    64.7% { transform: translate(309.2px, 829.9px) rotate(-77deg); }
    70.6% { transform: translate(319.5px, 808.7px) rotate(-49deg); }
    76.5% { transform: translate(338.9px, 795.6px) rotate(-21deg); }
    82.4% { transform: translate(362.2px, 792.1px) rotate(2deg); }
    88.2% { transform: translate(385.2px, 797.3px) rotate(23deg); }
    94.1% { transform: translate(405.1px, 809.9px) rotate(42deg); opacity: 0.7; }
    100.0% { transform: translate(420.0px, 828.3px) rotate(51deg); opacity: 0; }
}

/* Gischt an der Lippe: Die Tropfen werden nach rechts geworfen und fallen
   beschleunigt nach unten, dabei verblassen sie. */
.surfer-drop {
    fill: #f8fdfd;
    opacity: 0;
    animation: surfer-drop-fall var(--drop-dur, 2.2s) ease-in infinite;
    animation-delay: var(--drop-delay, 0s);
}

@keyframes surfer-drop-fall {
    0% { opacity: 0; transform: translate(0, 0); }
    12% { opacity: 1; transform: translate(2px, -3px); }
    100% { opacity: 0; transform: translate(16px, 50px); }
}

/* Heckwelle (Aufgabe 69): Das Brett fährt mit der Spitze nach rechts, das
   Heck liegt links unter dem Schaum. Von dort fließt das Wasser schnell
   nach links weg, in einem sich öffnenden V: Der obere Arm läuft über
   die Wellenfläche nach oben links, der untere aufs offene Wasser. Die
   Linien starten am Heck (Drehpunkt rechts, damit sie beim Strecken dort
   ansetzen), werden länger und verblassen. Je Arm laufen zwei um einen
   halben Takt versetzte Linien, so reißt der Strom nicht ab. Mit 1,5 s ist
   der Takt deutlich schneller als die Strömung der Welle. Hell auf dem
   dunklen Wellenwasser, dunkel auf dem hellen Schaum. */
.surfer-stern-line {
    fill: none;
    stroke: #e6f4f3;
    stroke-width: 3;
    stroke-linecap: round;
    opacity: 0;
    transform-box: fill-box;
    transform-origin: 100% 50%;
}

.surfer-stern-line--dark {
    stroke: #3f8a90;
}

.surfer-stern-line--up   { animation: surfer-stern-flow-up 1.5s linear infinite; }
.surfer-stern-line--down { animation: surfer-stern-flow-down 1.5s linear infinite; animation-delay: -0.2s; }
.surfer-stern-line--up.surfer-stern-line--late   { animation-delay: -0.75s; }
.surfer-stern-line--down.surfer-stern-line--late { animation-delay: -0.95s; }

@keyframes surfer-stern-flow-up {
    0% { opacity: 0; transform: translate(0, 0) scaleX(0.5); }
    12% { opacity: 0.8; }
    65% { opacity: 0.5; }
    100% { opacity: 0; transform: translate(-110px, -40px) scaleX(1.6); }
}

@keyframes surfer-stern-flow-down {
    0% { opacity: 0; transform: translate(0, 0) scaleX(0.5); }
    12% { opacity: 0.8; }
    65% { opacity: 0.5; }
    100% { opacity: 0; transform: translate(-110px, 34px) scaleX(1.6); }
}

/* Fahrt über die Szene (Aufgabe 70): Die Hülle .surfer-travel trägt die
   Position und die Spiegelung; die Figur selbst (.surfer) steht mit ihrem
   Anker bei x=0. js/surfer.js rechnet aus der Fenstergröße die Start- und
   Zielposition (--surfer-x0, --surfer-x1, in Szeneneinheiten) und die
   Dauer (--surfer-cycle) aus und setzt .is-travelling. Ohne Skript oder
   bei reduzierter Bewegung steht der Surfer still an --surfer-x0; die
   Rückfallwerte hier halten ihn auch dann im Bild (Hochformat: weiter
   links, weil dort nur der linke Szenenausschnitt sichtbar ist). */
.surfer-travel {
    --surfer-x0: 900px;
    --surfer-x1: 900px;
    --surfer-cycle: 90s;
    transform: translateX(var(--surfer-x0));
}

@media (max-aspect-ratio: 1 / 1) {
    .surfer-travel {
        --surfer-x0: 470px;
    }
}

/* Hinfahrt, Umklappen, Rückfahrt gespiegelt (Aufgaben 70, 71). Am Ende der
   Hinfahrt wechselt scaleX sofort von 1 auf -1, es gibt keine Drehung. Der
   Pivot liegt am Körper (ca. 30 Einheiten links vom Brettmittelpunkt),
   so bleibt er beim Umklappen an Ort und Stelle. Beginn und Ende stimmen
   überein (Ende gespiegelt, Anfang nicht): Der Wechsel zurück passiert
   ebenfalls sofort am Schleifenanfang, die Schleife ist nahtlos. Gleichmäßig
   (linear) statt gebremst, weil an der Wende nichts ausläuft. Die negative
   Verzögerung (25 % des Zyklus) lässt die Seite mitten in der ersten
   Hinfahrt starten. */
.surfer-travel.is-travelling {
    animation: surfer-travel var(--surfer-cycle) linear infinite;
    animation-delay: calc(var(--surfer-cycle) * -0.25);
}

@keyframes surfer-travel {
    0% { transform: translateX(var(--surfer-x0)) translateX(-29.5px) scaleX(1) translateX(29.5px); }
    50% { transform: translateX(var(--surfer-x1)) translateX(-29.5px) scaleX(1) translateX(29.5px); }
    50.001% { transform: translateX(var(--surfer-x1)) translateX(-29.5px) scaleX(-1) translateX(29.5px); }
    100% { transform: translateX(var(--surfer-x0)) translateX(-29.5px) scaleX(-1) translateX(29.5px); }
}

/* Wechsel fahrend / sitzend (Aufgabe 79): Zwei Szenen teilen sich die
   Stelle im Bild. js/surfer.js blendet etwa jede Minute die eine aus und die
   andere ein: Zuerst bekommt die sichtbare Szene .is-faded (Opacity 0 mit
   Übergang), danach .is-gone (display none: wird nicht gezeichnet und der
   Beobachter in js/surfer.js pausiert ihre Animationen); die andere Szene
   verliert beide Klassen in umgekehrter Reihenfolge. */
.surfer-scene {
    transition: opacity 2s ease-in-out;
}

.surfer-scene.is-faded {
    opacity: 0;
}

.surfer-scene.is-gone {
    display: none;
}

/* Position des Sitzenden: möglichst mittig im sichtbaren Bild.
   js/surfer.js setzt --surfer-sit-x auf die Mitte des sichtbaren
   Szenenausschnitts; die Rückfallwerte gelten ohne Skript (im Hochformat
   ist nur der linke Ausschnitt sichtbar). */
.surfer-sit {
    --surfer-sit-x: 960px;
    transform: translateX(var(--surfer-sit-x));
}

@media (max-aspect-ratio: 1 / 1) {
    .surfer-sit {
        --surfer-sit-x: 300px;
    }
}

/* Sitzender Surfer: sechs Töne für Haut, Badehose, drei für das Brett und
   der Wasserschatten, nachgezeichnet aus dem dritten Mockup. */
.surfer-sit-shadow       { fill: #659297; }
.surfer-sit-shadow2      { fill: #74a3a8; }
.surfer-sit-board-dark   { fill: #4c5850; }
.surfer-sit-board-mid    { fill: #7c786b; }
.surfer-sit-board-top    { fill: #99947e; }
.surfer-sit-skin         { fill: #b68d6a; }
.surfer-sit-skin-shade   { fill: #a47d60; }
.surfer-sit-skin-shade2  { fill: #8c674c; }
.surfer-sit-shorts       { fill: #eb3844; }
.surfer-sit-shorts-shade { fill: #b32d37; }
.surfer-sit-hair         { fill: #060706; }

/* Dynamik: Um die Beine laufen dieselben ausfadenden Wellenringe wie am
   Brett des fahrenden Surfers (.surfer-ring, siehe Aufgabe 66). Der
   Sitzende schaukelt zusätzlich ganz leicht auf dem Wasser. */
.surfer-sit-rider {
    animation: surfer-sit-bob 5s ease-in-out infinite;
}

@keyframes surfer-sit-bob {
    0%,
    100% { transform: translateY(0); }
    50% { transform: translateY(-1.6px); }
}

.surfer-sit.is-paused * {
    animation-play-state: paused;
}

.surfer.is-paused * {
    animation-play-state: paused;
}

@media (prefers-reduced-motion: reduce) {
    .surfer-wave-dark,
    .surfer-wave-wall,
    .surfer-deep,
    .surfer-board,
    .surfer-wave-foam,
    .surfer-body,
    .surfer-wake,
    .surfer-stern,
    .surfer-sit-rider,
    .surfer-ring,
    .surfer-trail,
    .surfer-particle,
    .surfer-drop,
    .surfer-stern-line,
    .surfer-travel.is-travelling {
        animation: none;
    }

    .surfer-scene {
        transition: none;
    }
}
