CSS Slideshow mit Keyframes

Slideshow – Bilderwechsel – mit CSS Keyframes

Viele Animationen, die früher nur mit Javascript ausgeführt werden konnten, können wir heute CSS überlassen. Aber nur keine hohen Erwartungen: Genauso wie Animationen mit Javascript können CSS-Animationen mit reinem CSS trickreich sein. Fangen wir also mit einer einfachen Slideshow mit dem Einblenden von drei Bildern an.

HTML: Responsive Bilder mit srcset und sizes

Animationen mit CSS sind nicht so flexibel wie Slideshows, die von Javascript betrieben werden. Das HTML ist allerding wirklich schlicht. Die Bilder nutzen srcset und sizes, um kleinere bzw. größere Bilder je nach Größe des Viewports zu setzen.

Die Bilder sitzen in einem Custom Element <css-slides>, einem eigenen HTML-Tag. Custom Elements kapseln ein HTML-Element ein, um tiefes Verschachteln von div-Tags und zahllosen Klassen zu vermeiden. Sie bestehen immer aus einem Paar von öffnenden und schließenden Tags und der Name des Custom Element muss einen Bindestrich enthalten.

Wem das Custom Element unheimlich ist, kann es durch ein div class="css-slides" ersetzen.

<css-slides>
	<img loading="lazy" src="garten-460.jpg" width="460" height="358" alt="garten-460"
		 srcset="garten-460.jpg 460w,
				 garten-980.jpg 980w"
		sizes="(max-width: 460px) 100vw, 980px">
	<img loading="lazy" src="gelber-nachen-460.jpg" width="460" height="358" alt="gelber-nachen-460"
		 srcset="gelber-nachen-460.jpg 460w,
				 gelber-nachen-980.jpg 980w"
		sizes="(max-width: 460px) 100vw, 980px">
	<img loading="lazy" src="schuessel-obst-460.jpg" width="460" height="358" alt="schuessel-obst-460"
		 srcset="schuessel-obst-460.jpg 460w,
				 schuessel-obst-980.jpg 980w"
		sizes="(max-width: 460px) 100vw, 980px">
</css-slides>
garten-460 gelber-nachen-460 schuessel-obst-460

Zeitplan der Animation

Die Animation blendet Bilder innerhalb einer Sekunde ein, zeigt sie für eine Sekunde und blendet sie eine Sekunde lang aus, während sie gleichzeitig das nächste Bild eingeblendet.

CSS Slideshow Taktung

Die Dauer der Animation ergibt sich aus

  • + eine Sekunde einblenden
  • + eine Sekunde sichtbar
  • + ----------------------
  • = 2 Sekunden pro Bild
  • * 3 Bilder
  • + ----------------------
  • = 6 Sekunden insgesamt.

Die Animation des zweiten Bildes beginnt nach zwei Sekunden, die Animation des dritten Bildes nach vier Sekunden. Das zweite Bild beginnt mit einer Verzögerung von zwei Sekunden, das dritte Bild mit einer Verzögerung von vier Sekunden.

Animation takten

Mehr Flexibilität zieht ein, wenn wir die Dauer der Animation mit 100% angehen und die Aktionen takten.

Keyframes takten in Prozentwerten
100 / Dauer der Animation = Prozentsatz für eine Sekunde

Soll das fadeIn weiterhin eine Sekunde dauern, die Anzeige für zwei Sekunden stehen, dauert die Animation von drei Bildern 9 Sekunden. Eine Sekunde wird mit 100 / 9 zum Sekundentakt: 11.11% der Animatonsdauer.

  • + eine Sekunde einblenden
  • + 2 Sekunden sichtbar
  • + ----------------------
  • = 3 Sekunden pro Bild
  • * 3 Bilder
  • + ----------------------
  • = 9 Sekunden insgesamt.
@keyframes fade {
	0%      { opacity: 0; }  /** fadeIn beginnt            **/
	11.11%  { opacity: 1; }  /** Bild steht                **/
	33.33%  { opacity: 1; }  /** Bild bleibt zwei Sekunden **/
	44.44%  { opacity: 0; }  /** fadeOut beendet           **/
	100%    { opacity: 0; }
}

Das CSS für die Animation der Bilder

css-slides img { 
    opacity:0; 
    animation-name: fade; 
    animation-duration: 9s; 
    animation-iteration-count: infinite; 
    position:absolute; 
    left:0; 
    right:0; 
}

Am Ende folgt noch die Animation der einzelnen Bilder mit ihre individuellen Verzögerung.

css-slides img:nth-child(1) { animation-delay: 0s; }
css-slides img:nth-child(2) { animation-delay: 3s; }
css-slides img:nth-child(3) { animation-delay: 6s; } 

Breite und Höhe der Slideshow

Die Bilder innerhalb von css-slides sind absolut positioniert, css-slides muss relativ positioniert werden. Ob das umfassende Element der Slideshow in einem klassischen div-Tag oder in einem Custom Element css-slides liegt, spielt keine Rolle.

css-slides braucht noch eine Angabe zur Höhe, die in gleicher Weise wie ein iframe durch padding-bottom berechnet wird.

css-slides {
	position:relative;
	height:0;
	padding-bottom: calc(286/460 * 100%);
	overflow:hidden;
	display:block;
}

Am Rande: calc(286/460 * 100%) berechnet das Seitenverhältnis der Slideshow-Bilder (statt direkt den Prozentsatz zu schreiben).

Das geht allerdings heute einfacher mit CSS aspect-ratio, bei dem wir direkt das Verhältnis von Breite zu Höhe einsetzen.

aspect-ratio: 460/286;