„HTML5-Ads sind die Zukunft!“ – Diese Aussage ist nicht ganz richtig. Denn HTML5 –Ads sind im mobilen Kontext bereits die Gegenwart.
Als Starthilfe für die Entwicklung dieser Werbemittel wurde diese Einführung geschrieben. Sie soll einen Überblick über aktuelle Techniken verschaffen, best practises aufzeigen, vor Fallstricken warnen und Dos & Dont's benennen. Zusätzlich demonstriert das Beispiel-Ad viele der empfohlenen Techniken. Es wird live auf dieser Seite gezeigt und kann zum Experimentieren heruntergeladen werden.
Die einzelnen Themengebiete werden jeweils durch eine Vielzahl von Links abgerundet, hinter denen sich zum einen weiterführende Artikel und zum anderen Tools und dienliche Ressourcen verbergen. Klicken lohnt sich, da diese Einführung letztlich nur einen Startpunkt für das komplexe Gesamtthema darstellt.

Beispiel-Ad

Quellcode des Beispiel-Ads herunterladen

HTML

HTML-Elemente bilden das Herzstück eines Ads. Je nach Werbeintegration wird der finale AdCode auf zwei verschieden Arten angelegt:
Wird das Ad innerhalb eines iFrame-Ad-Containers ausgespielt, sollte das Ad einem komplettes HTML-Dokument darstellen, d. h. es wird von den Elementen <!doctype>, <html>, <head>, <body> umschlossen.

<!DOCTYPE html>
<html>
<head>
  <title></title>
</head>
<body>
 ...
 Code des Werbemittels
 ...
</body>
</html>

Falls das Ad direkt in den DOM-Baum der Publisher-Seite integriert wird, darf das Ad nur als Code-Schnippsel angeliefert werden. In diesem Fall entfallen die umschließenden Elemente.

Viewport-Element

Das <viewport>-Element steuert die Eigenschaften des Anzeigebereichs: die Breite, die Skalierung und die Skalierbarkeit. Der Viewport sollte beim Testen und bei der Ausspielung im iFrame (siehe vorherigen Abschnitt) auf korrekte Werte gesetzt sein.

Weitere Erkärungen und Beispiele hier: http://html5-mobile.de/blog/meta-viewport-fuer-mobile-anpassen

ID- und Klassennamen

Zur Vermeidung von Namenskollisionen mit HTML-Elementen auf der Publisher-Seite, ist es nötig, dass alle vergebenen IDs und Klassennamen, z. B. durch ein Präfix, eindeutig bestimmt werden.
Im Beispiel-Ad wurden sämtliche IDs und Klassen mit dem Präfix "guideAd" erweitert:

<div class="guideAdSceneStart">
    <div class="guideAdHTML5LogoBlank"></div>
    <div class="guideAdHTML5Logo"></div>
    <div class="guideAdInstructions"></div>
</div>

JavaScript

JavaScript übernimmt den Logik-Teil eines Ads. Der Aufbau des Quellcodes unterliegt keiner bestimmten Form. Damit beim Ausspielen des Ads auf der Publisher-Seite keine Nebeneffekte oder Konflikte auftreten, sollten folgende Punkte eingehalten werden:

  • document.write() ist tabu! Mobile Werbung wird asynchron geladen und ausgeführt, d. h. die Werbung wird erst geladen, nachdem die Publisher-Seite fertig geladen ist. Der Befehl document.write() führt in diesem Falle zu einem Fehler oder einer fehlerhaften Darstellung der Seite. Alternativ empfiehlt sich eine DOM-Manipulation mit dem Befehl .appendChild().

  • Funktionen und Variablen sollten in einem eigenen Namespace angelegt werden, um Namenskollisionen zu verhindern. Im Beispiel-Ad werden sämtliche Funktionen und Variablen innerhalb des Objekts guideAd angelegt:

    var guideAd = { ... };

  • Werden externe Ressourcen, wie Bilder, XML-, JSON-Dateien, per XMLHttpRequest bzw. AJAX geladen, müssen sie serverseitig für den Cross-Domain-Zugriff freigegeben werden.

    Siehe dazu auch: http://enable-cors.org/server.html

Tipp: Sämtliche mobilen Browser unterstützen den Befehl .querySelector(), welcher wesentlich mächtiger ist als das oft benutzte getElementById(). https://developer.mozilla.org/en-US/docs/Web/API/document.querySelector

jQuery & weitere Libraries

Bei Nutzung von jQuery und ähnlichen Libraries muss im Werbemittel auf ein bereits von der Publisher-Site geladenes Framework geprüft werden (und im Zweifel dieses genutzt werden). Falls die Site kein jQuery verwendet, darf ein eigenes Framework geladen werden.

Jede eingebundene Ressource vergrößert die zu ladene Datenmenge und verschmälert dadurch die User Experience. Deshalb sollte vor der Einbindung einer Library unbedingt geprüft werden, ob die gewünschte Funktionalität nicht auch durch reinen JavaScript-Code erzeugt werden kann. Oder ob eine spezielle mobil-optimierte Variante der Library existiert. Als leichtgewichtigere Alternative zu jQuery empfehlen wir folgende Frameworks - sie haben kleinere Dateigrößen bei ähnlichem Funktionsumfang:

Wer bislang ohne Libraries wie jQuery nicht zurecht kam, findet hier Hilfe für den Start in ein Leben ohne diese Hilfsmittel: http://blog.garstasio.com/you-dont-need-jquery/ und http://youmightnotneedjquery.com/.

Tipp: Das Javascript-Event click wird von den meisten Browsern mit einer kleinen Verzögerung (300ms) ausgeführt. Falls diese Verzögerung ein Problem darstellt, kann auf ein Workaround mit dem Event touchstart ausgewichen werden. Hintergrund und Lösungen werden hier aufgezeigt: http://www.sitepoint.com/5-ways-prevent-300ms-click-delay-mobile-devices/

JavaScript-Animationen & requestAnimationFrame

Es gibt zwei verschiedene Möglichkeiten Animationen in JavaScript umzusetzen:

  • Direkte Animation von HTML-Elementen durch Änderung der CSS-Eigenschaften
  • Einsatz des <canvas>-Elements

Für beide Möglichkeiten existieren Libraries und Frameworks, mit denen komplexe Animations-Logik, wie sie z. B. für Spiele benötigt wird, einfacher, übersichtlicher und schneller umgesetzt werden können.

Performance von JavaScript-Animation

Um eine optimale Performance zu erreichen, sollten JavaScript-Animationen die requestAnimationFrame-API des Browsers nutzen. Mehr Informationen dazu unter: requestAnimationFrame for Smart Animating

Event-Tracking

Zählpixel und Event-Tracker können per XMLHttpRequest oder durch das Erzeugen eines Image-Objekts angesprochen werden:

xmlhttp.onreadystatechange=function()
  {
  if (xmlhttp.readyState==4 && xmlhttp.status==200)
    {
    document.getElementById("myDiv").innerHTML=xmlhttp.responseText;
    }
  }
xmlhttp.open("GET","ajax_info.txt",true);
xmlhttp.send();
var trackingPixel;
trackingPixel = new Image();
trackingPixel.src = „http://...“;
Standard-Zählpixel können selbstverständlich direkt per <img>-Tag eingebunden werden.

CSS

Mit Hilfe der Cascading Style Sheets, kurz CSS, werden HTML-Elemente gestylt. Eine gute Einführung in den umfangreichen Katalog von Anweisung findet sich hier: http://www.w3schools.com/css/css_intro.asp

Expandables und der z-Index

Der z-Index definiert die Reihenfolge der Überlappungen von Layern im CSS. Werbemittel, die sich über den Seiteninhalte legen, sollten auf einen höheren z-Index gesetzt werden als die überlagerten Inhalte. Ein ‚korrekter Wert’ läßt sich nicht definieren, da die z-Indices von Seite zu Seite variieren. Erfahrungsgemäß empfiehlt sich das Testen von Werten über 1000.

Animationen

Mit CSS lassen sich Animationen mit geringem Aufwand umsetzen. Im Beispiel-Ad wird die Aufforderung zum Kippen des Handys mittels Keyframes animiert:

.guideAdInstructions {
  position: absolute;
  top: 50px;
  left: 10px;
  width: 120px;
  height: 20px;
  background: transparent url('images/instructions.png') no-repeat;
  background-size: 100%;

  /* 
  * Definition einer unendlichen Animation
  */
  
  -webkit-animation-name: drehung;
  -webkit-animation-duration: 1000ms;
  -webkit-transform-origin: 50% 50%;
  -webkit-animation-iteration-count: infinite;
  -webkit-animation-timing-function: ease;
}

/* 
* Definition der Keyframes der Animation
*/

@-webkit-keyframes drehung {
  0% { -webkit-transform: rotate(3deg);}
  50% { -webkit-transform: rotate(-3deg);}
  100% { -webkit-transform: rotate(3deg);}
}

Bilder

Bilder sind ein Hauptbestandteil der allermeisten Ads. Bei der Wahl des richtigen Formats sollte immer zwischen Qualität und Dateigröße abgewogen werden.

Unterstützung für Retina- und HDPI-Displays

Alle moderenen Smartphones verfügen heuzutage über ein hochauflösendes Display. Damit Bilder auf diesen Geräten knackigscharf aussehen, sollten sie in hoher, z. B. doppelter Auflösung gespeichert werden. Die Einbindung kann, wie hier im Beispiel-Ad, über CSS erfolgen:

.guideAdHTML5Logo {
  position: absolute;
  top: 6px;
  left: 128px;
  width: 45px;
  height: 64px;
  background: transparent url('images/html5_logo.png') no-repeat;
  background-size: 100%;
}
Vergleich zwischen der einfachen Auflösung (links) und der 'doppelten' Auflösung

SVG: Vektoren im Web

Scalable Vector Graphics, kurz SVG, ist ein skalierbares Vektorgrafikformat. Es eignet sich besonders für Logos, CTAs, Icons und Navigationselemente sowie textbasierte Grafiken. Vor Gebrauch sollte die Unterstüzung des SVG-Formats in den jeweiligen Browsern getestet werden, da es teilweise zu Darstellungsunterschieden kommen kann.

HTTP-Request reduzieren mit CSS-Sprites

Die Verwendung von CSS-Sprites ist eine beliebte Technik um die Anzahl der Serveranfragen zu reduzieren und um dadurch Ladezeit zu sparen. Der Einsatz von Sprites ist insbesondere im mobilen Umfeld sinnvoll, da netzbedingt Serveranfragen eine hohe Latenz aufweisen. Werbemittel, die viele kleine Grafikenressourcen laden, sollten dringend diese Technik einsetzen.

Und so funktioniert es: Das Sprite ist eine Grafikdatei, die viele kleinere Grafikelemente, wie z. B. Icons, zusammenfasst. Durch die Verwendung von den CSS-Anweisungen background-image und background-position werden Bildbereiche so zugewiesen, dass nur ein Grafikelement der Gesamtgrafik angezeigt wird. Auf diese Weise teilen sich verschiedene HTML-Elemente eine einzelne Grafikressource.

Ausschnitt eines Sprites von Yahoo.com
Mehr zu dem Thema CSS-Sprites: http://css-tricks.com/css-sprites/

Data URI: eingebettete CSS Bilder

Grafiken über Data-URI zu integrieren ist eine weitere Methode um Serveranfragen zu 'sparen'. Dazu wird die Grafik nicht als Datei-Ressource abgelegt und geladen, sondern die reinen Daten der Grafik werden mit dem Kodierverfahren Base64 kodiert und direkt als background-image:url(data:...) in das CSS geschrieben. Diese Technik empfiehlt sich vor allem für kleine Grafiken, wie z. B. Icons.

Für sehr kleine Bilder, z. B. Pfeil-Icons, kann das Bild direkt im CSS geschrieben werden. Das Bild wird dazu Base64-codiert und dann als background-image:url(data:...) eingefügt.

Mehr zum Thema Data-URI: http://css-tricks.com/data-uris/

Mobile Besonderheiten

Ads in Apps & ORMMA/MRAID

HTML5 Werbemittel können auch in Apps ausgespielt werden. Folgendes sollte dabei beachtet werden:

  • ORMMA (Open Rich Media Mobile Advertising) und MRAID (Mobile Rich Media Ad Interface Definitions) sind standardisierte APIs für In-App-Werbeformen, die Zugriff auf Gerätefunktionen und -eigenschaften erlauben. Soll beispielsweise das Werbemittel expandieren oder sich über den App-Inhalt legen, muss das Ad ORMMA- oder MRAID-kompatibel sein und die nötigen Befehle ausführen können.
    Mit Hilfe der APIs ist es ebenfalls möglich auf spezielle Funktionen der Geräte zuzugreifen, z. B. auf die Erstellung eines Kalendereintrags.
    Sowohl MRAID als auch ORMMA wurden vom Interactive Advertising Bureau (IAB) entwickelt und gelten als Branchenstandard. Da ORMMA der Vorläufer von MRAID ist, ist das modernere MRAID als state-of-the-art anzusehen.
  • Die meisten App öffnen Links (...) in einem in-App-Browser

Bewegungssensoren und Kompass-Daten auslesen

Die meisten mobilen Geräte besitzen Sensoren, mit denen die Beschleunigung im Raum gemessen werden kann. Durch diese Bewegungssensoren, auch Accelerometer genannt, kann die Beschleunigung des Geräts entlang der X-, Y- und Z-Achse gemessen werden. Das Beispiel-Ad zeigt, wie man mithilfe des Javascript-Codes auf diese Werte Zugriff erhalten kann:

window.addEventListener('devicemotion', guideAd.onDeviceMotion, false);
...
onDeviceMotion: function(e) {
  var x = -Math.round(e.accelerationIncludingGravity.x * 10000) / 10000;

  // Da bei Android-Geräten die Achsen-Richtung vertauscht ist, wird der Wert ggf. negiert.
  if (guideAd.cfg.isAndroid) {
    x = -x;
  }
  guideAd.arrayX.push(-x * 40);
  guideAd.arrayX.splice(0, 1);
  guideAd.animateLogo(guideAd.average10(guideAd.arrayX));
}

Auf ähnliche Art und Weise lassen sich auch die Kompass-Informationen auslesen, wenn dies vom Gerät unterstützt wird:

window.addEventListener('deviceorientation', function(e) {
  cA.headings.push(e.webkitCompassHeading);
}, false);

Nützliches