CSS Sprites einfach erklärt

Die Zeiten ändern sich.

Dieser Beitrag scheint älter als 15 Jahre zu sein – eine lange Zeit im Internet. Der Inhalt ist vielleicht veraltet.

Die Webkrauts haben das Thema „Hoverffekte mit CSS-Sprites“ schon vor langer Zeit aufgegriffen und erklärt, ausführlich. Dies soll hier nicht statt finden. Aber es ist immer noch eine relativ selten verwendete Technik und viele arbeiten dann mit Lösungen via JavaScript um die Bilder zum richtigen Zeitpunkt zu laden. Dies ist nicht nötig, mit Hilfe der Technik der CSS-Sprites kann man den unschönen Effekt, der auftritt bei MouseOver von Bildern als Link, beheben. Das ist wenig im Aufwand und bringt viel im Aussehen und Benutzerfreundlichkeit.

Um auf diese Technik nochmal und vereinfacht aufmerksam zu machen, habe ich mal ein sehr einfaches und, so denke ich, überschaubares Beispiel erstellt. Ansehen, verstehen und Nutzen war die Devise.
Die vielen kleinen Spielereien, die dann daraus resultieren sind auf vielen Beiträgen im Netz nachzulesen.

Die Nutzung von CSS-Sprites hat Vorteile:

  • Kein Einsatz von clientseitigen Sprache wie JavaScript nötig
  • Kein MouseOver-Code in den Links
  • Bilder liegen vor und der lästige Verlagerungseffekt entfällt
  • weniger Bilder beim Download und im Einsatz, wenn man es effektiv nutzt
  • Bessere Nutzung der Bandbreite beim Besucher

So geht es

In wenigen Punkten und Erklärungen ist die Lösung zu sehen. Wie das ganze dann in Benutzung aussieht, dass sieht man oben am Start des Artikels oder im Beispiel in der Experimente-Box.

Das Bild kann natürlich mehrfach verwendet werden. Eventuell benötigt man das Logo auch in anderen Darstellungen auf der Seite, ohne hover-Effekt. Damit lohnen sich solche Lösungen richtig. Man nutzt dann eben nur den Bereich, der zu sehen sein soll.

Sprite Beispiel

Bild

125px breit und 60px hoch; 5px Abstand sind zwischen den einzelnen Bildern des Ganzen

CSS Style

Im Grund greift das CSS nur auf das ID zu und erzeugt den Effekt durch die Pseudeklasse hover.
Die Höhe und Breite ergibt sich aus der Größe des eigentlichen Einzelbildes, in diesem Beispiel 60px.


#image-link {
	width: 60px;
	height: 60px;
	text-decoration: none;
	display: block;
	background: url('images/fb-sprite.png') 0 0;
}
	
#image-link:hover, #image-link:active {
	background-position: 60px 0;
}

 
Die Angabe 0 0 muss bei background nicht vergeben werden; nur wenn es eine Verschiebung geben soll. Genauso könnte man das Beispiel hier auch anders herum nutzen. Dafür müsste man lediglich die Positionswerte für die ID image-link tauschen.


#image-link {
	width: 60px;
	height: 60px;
	text-decoration: none;
	display: block;
	background: url('images/fb-sprite.png') 60px 0;
}
	
#image-link:hover, #image-link:active {
	background-position: 0 0;
}

HTML Code

In diesem Bespiel dient ein einfacher Link als Demonstration, natürlich kann man hier alle bekannten Möglichkeiten aufgreifen und beispielsweise schöne Navigation erstellen.


<a href="#" id="image-link">&nbsp;</a>

Von Frank Bültge

bueltge.de [by:ltge.de] wird von Frank Bültge geführt, administriert und gestaltet. Alle Inhalte sind persönlich von mir ausgewählt und erstellt, nach bestem Gewissen und Können, was die Möglichkeit von Fehlern nicht ausschließt.

40 Kommentare

  1. Der große Vorteil liegt meiner Meinung nach darin, dass der :hover-Zustand bereits mitgeladen wird, da ja direkt die komplette Grafik beim Seitenaufbau geladen wird. So lassen sich auch komplette Navigationen inkl. aller Schaltflächen (link, hover, active, evtl visited) in einer Grafik realisieren. Je nach Link wird dann nur die entsprechende Position in der Grafik angegeben.
    Beim hinzufügen von Navigationspunkten oder einer grafischen Überarbeitung spart man hierbei vor allem massiv Zeit, wenn nur eine Grafik ausgetauscht werden muss.

  2. Naja ich finde das man solche Hover-Effekte mit Javascript einfacher bekommt. Ich habe eine Javascript-Funktion die mit der ID des Bildes arbeitet und dann die entsprechende Hover-Grafik nimmt. Bei CSS wäre das viel mehr Code.

    Und mal ehrlich, wenn auf jeder Webseite Javascript verwendet wird, warum sollte ich das dann nicht auch nutzen?

  3. @Jonas: sehe ich auch so und habe es daher nochmal in extrem einfacher Form dargestellt.

    @gr4y: Weil man es oft deaktiviert – Theme Sicherheitsrisiko, zumindest im Unternehmensumfeld.

  4. @Jared: Das Prinzip ist das gleiche. Das Bild kannst du zig mal verwenden. Man könnte auch im Bild viele Details nutzen und nur den bereich nutzen, den man benötigt. So lädt man für mehrere Anwendungen nur ein Bild. Im hiesigen Bsp. sind es nur zwei Bilder, die man aber schon 4 mal nutzt.

  5. Wie schön, dass mein Beispiel hier aufgegriffen wird 🙂
    Ach ja: Der IE unterstützt :hover ja nur unzureichend (siehe hier) – daher müsste man ja in jedem Fall einen Link nutzen, um auch dort den Effekt zu erhalten (oder?).

    Der Unterschied zu meiner Idee ist ja die Nutzung des Hintergrundbildes, während ich normal eingebundene Bilder verwende – was bei dynamisch eingebundenen Bildern sicherlich einiges an Arbeit spart 🙂

  6. @Markus: IE-Problem ist leider nicht weg zu diskutieren. Auf die vielen kleinen Details gehe ich fast nie ein, weil ich den IE vernachlässige (damit soll keine Diskussion entfacht werden, ich weiß, dass Können Agenturen und Firmen etc. nicht) – aber ich, denn das hier ist privat.
    Den Unterschied habe ich erkannt, musste es nur mal in Ruhe lesen. Worauf ich hinaus will, ist die mehrmalige Verwendung von Bildern. Bei geschickter Überlegung kann man so eine Menge an Last sparen.
    LG Frank

  7. Warum sparen CSS-Sprites Bandbreite? Ich sehe schon die vielen kunterbunten Navigationen, bei denen 50% der Bilder nie das Licht des Internets erblicken weil niemand drauf klickt.
    Deiner Theorie folgend, wäre es das beste alle Hintergrundbilder in einem Sprite zu vereinigen und dann immer nur das Sprite zu verschieben. Ergebnis wäre dann wahrscheinlich ein riesiges Bild (1MB? 2MB? 😉 ). Bei jedem Hover müsste man trotzdem warten bis das komplette Sprite geladen wurde. Einspareffekt: Null.

    Ich bleibe lieber dabei und verpasse im CSS jedem Zustand seine eigene Grafik. Wirklich Interessant finde ich den von Jared verlinkten Lösungsansatz. Bei Links und anderen nebensächlichen Effekten finde ich CSS-Sprites hingegen einfach übertrieben.

  8. @Ralf: Warum man besser CSS-Sprites statt einzelner Bilder benutzen sollte erklärt Chris Coyier sehr anschaulich in einem ausführlichen Artikel. Man verringert durch Sprites die Anzahl der http-Requests, dadurch kann die Seite schneller geladen werden.

    Abgesehen davon: Wenn für eine Navigation Hintergrundbilder genutzt werden, dann würde ich mir die Mühe machen, eine Liste mit entsprechenden Einträgen per CSS in die einzelnen Hintergrund-Bilder einzupassen. Dann ließe sich ein einziges CSS-Sprite für alle Navigationselemente nutzen, was letztendlich eine massive Ersparnis an http-Requests sowie zu ladendem Content ist. Vom zu schreibenden Code mal ganz abgesehen…

    Ach ja: Schön, dass dir mein Beispiel gefällt 🙂

  9. Ich will die Technik an sich nicht verteufeln. Man kann sie, wie gezeigt, sehr sinnvoll einsetzen. Hier wird aber evt. das falschen Beispiel (Navigation) verwendet. Um es mal überspitzt auszudrücken: Jeder wird mit diesem Beispiel anfangen und es ausbauen. Am Ende wird nur noch eine einzige Grafik geladen um möglichst viele HTTP-Requests einzusparen und alle Grafiken/Hintergründe werden über ein einziges CSS-Sprite realisiert.
    Dummerweise werden i.d.R. alle Seitenelemente im Browsercache abgelegt. Und dann schlummert dort eine riesige Grafik von der u.U. zwei oder drei kleine Bereiche verwendet werden. Und genau hier liegt wohl auch der Denkfehler. Denn es wird ja nicht bei jedem Mouse-Hover ein HTTP-Request abgesetzt, sondern die Grafik wird aus dem Cache geholt. Somit habe ich vielleicht 10 HTTP-Request gespart. Dafür aber jede Menge an unnötigen Daten übermittelt.
    Am Ende zahlt dann der Seitenbetreiber ggf. sogar noch drauf. Denn er versendet unnötig Daten und erhöht somit den Traffic. Zudem müllt er unnötig die Festplatten der Besucher voll. Bei den heutigen Festplatten wahrscheinlich kein merklich großer Effekt. Aber schauen wir uns mal den Asus EEE-PC an. Der muss alles in 4GB Flashspeicher ablegen. Ist der Speicher voll, holt er sich die Grafik jedesmal neu. Hätte man nun alle Grafiken in ein einziges CSS-Sprite gepackt, würden Besucher mit einem EEE-PC schnell ins Hintertreffen geraten. EEE-PC-Benutzer surfen gerne von Unterwegs, dazu sind die winzlinge ja wie gemacht. Denkt man dann mal an die volumenbezogenen Tarife fürs mobile Surfen, würde ich als Besucher schnell mal stinkig werden wenn mir plötzlich jede Webseite ihr komplettes Grafikreportoir um die Ohren haut.

  10. Ich weiß nicht in was für Relationen du denkst. Wo ist bei einer Menügrafik von rund 72 kB das Problem (siehe Apple)? Auf die kommst du genauso, also würdest du jede Grafik einzeln nutzen – und die werden auch in deinen Cache geladen, vor allem, wenn du darauf wert legst, dass der :hover-Status ohne Flackern stattfinden soll, dann lädst du mindestens die Hälfte aller Grafiken in deiner Situation vor.

    So, und nun vergleichen wir das mit einem einzigen Request bei einer Grafik. Hmm, lässt sich meiner Meinung nach nicht mehr viel zu sagen. Ergo hat man mit einem Sprite mehr gespart als mit dutzenden Einzelgrafiken.

    Wie gesagt, deine Relationen passen nicht. Du redest von 1–2 MB pro Grafik, was völliger Quatsch ist.

  11. Ralf ich bin da uneingeschränkt deiner Meinung. Unabhängig davon, grade bei einer Navi habe ich dann *Schriftvergrößerung* ausgeschaltet, oder die Bildchen sehen sehr „kreativ“ aus.

    Auch private Seiten werden von IE usern betrachtet. 😉 Wenn ich schau wann ich den meisten Traffic habe, arbeiten 90% der Leute nur mehr nächtens, — 😉

    lg

Kommentare sind geschlossen.