Web Animations API-Verbesserungen in Chromium 84

Orchestrierte Animationen mit Versprechen, Leistungsverbesserungen durch austauschbare Animationen, flüssigere Animationen mit zusammengesetzten Modi und vieles mehr

Kevin Ellis
Kevin Ellis

Bei richtiger Anwendung verbessern Animationen die Wahrnehmung und Erinnerung Ihrer Marke durch die Nutzer, leiten Nutzeraktionen an, erleichtern Nutzern die Navigation in Ihrer App und bieten so einen digitalen Kontext.

Die Web Animations API ist ein Tool, mit dem Entwickler imperative Animationen mit JavaScript schreiben können. Es wurde geschrieben, um sowohl CSS-Animationen als auch Übergangsimplementierungen zu unterstützen und die Entwicklung zukünftiger Effekte sowie die Erstellung und zeitgesteuerte Erstellung vorhandener Effekte zu ermöglichen.

Während Firefox und Safari bereits alle Spezifikation Funktionen implementiert haben, bietet Chromium 84 eine Reihe bisher nicht unterstützter Funktionen für Chrome und Edge, die eine browserübergreifende Interoperabilität ermöglichen.

Die Web Animations API kam im Juli 2014 erstmals in der Version 36 in Chromium vor. Die Spezifikation ist jetzt in Version 84 vollständig. Sie wird im Juli 2020 eingeführt.
Die lange Geschichte der Web Animations API in Chromium.

Erste Schritte

Das Erstellen einer Animation über die Web Animations API sollte mit @keyframe-Regeln vertraut sein. Zuerst müssen Sie ein Keyframe-Objekt erstellen. So könnte in CSS folgendermaßen aussehen:

@keyframes openAnimation {
  0% {
    transform: scale(0);
  }
  100% {
    transform: scale(1);
  }
}

sieht in JavaScript so aus:

const openAnimation = [
  { transform: 'scale(0)' },
  { transform: 'scale(1)' },
];

Hier legen Sie Parameter für Animationen in CSS fest:

.modal {
  animation: openAnimation 1s 1 ease-in;
}

die Sie in JS festlegen:

document.querySelector('.modal').animate(
    openAnimation, {
      duration: 1000, // 1s
      iterations: 1, // single iteration
      easing: 'ease-in' // easing function
    }
);

Die Menge an Code ist ungefähr gleich, aber mit JavaScript haben Sie ein paar Superkräfte, die Sie mit CSS allein nicht haben. Dazu gehört die Möglichkeit, Effekte zu sequenzieren und den Wiedergabestatus besser zu steuern.

Über element.animate()

Allerdings ist die Web Animations API nach dem Update nicht mehr auf Animationen beschränkt, die über element.animate() erstellt wurden. Auch CSS-Animationen und -Übergänge lassen sich bearbeiten.

getAnimations() ist eine Methode, mit der alle Animationen für ein Element zurückgegeben werden, unabhängig davon, ob es über element.animate() oder über CSS-Regeln (CSS-Animation oder Übergang) erstellt wurde. Hier ist ein Beispiel, wie das aussehen könnte:

Zuerst "get" für die Keyframes für den Übergang, um zu bestimmen, von wo aus der Übergang erfolgt. Dann erstellen Sie zwei neue Deckkraftanimationen, um den Überblendungseffekt zu aktivieren. Sobald das Überblenden abgeschlossen ist, löschen Sie die Kopie.

Animationen mit Versprechen orchestrieren

In Chromium 84 gibt es jetzt zwei Methoden, die mit Promise verwendet werden können: animation.ready und animation.finished.

  • Mit animation.ready kannst du warten, bis ausstehende Änderungen wirksam werden. Das heißt, du kannst zwischen Wiedergabesteuerungsmethoden wie Wiedergabe und Pause wechseln.
  • animation.finished ermöglicht die Ausführung von benutzerdefiniertem JavaScript-Code nach Abschluss einer Animation.

Fahren wir mit unserem Beispiel fort und erstellen mit animation.finished eine orchestrierte Animationskette. Hier haben Sie eine vertikale Transformation (scaleY), gefolgt von einer horizontalen Transformation (scaleX), gefolgt von einer Änderung der Deckkraft eines untergeordneten Elements:

Transformationen und Deckkraft auf ein öffnendes modales Element anwenden. Demo zu Codepen ansehen
const transformAnimation = modal.animate(openModal, openModalSettings);
transformAnimation.finished.then(() => { text.animate(fadeIn, fadeInSettings)});

Wir haben diese Animationen mithilfe von animation.finished.then() verkettet, bevor die nächste Animation in der Kette ausgeführt wird. Auf diese Weise werden die Animationen der Reihe nach angezeigt und Sie wenden Effekte sogar auf verschiedene Zielelemente mit unterschiedlichen Optionen (z. B. Geschwindigkeit und Einfachheit) an.

In CSS wäre die Neuerstellung umständlich, insbesondere wenn eindeutige, aber sequenzierte Animationen auf mehrere Elemente angewendet werden. Sie müssen @keyframe verwenden, die richtigen Prozentsätze für das Timing zur Platzierung der Animationen aussortieren und animation-delay verwenden, bevor die Animationen in der Sequenz ausgelöst werden.

Beispiele: Wiedergeben, Pausieren und Rückwärtsgang

Was geöffnet werden kann, sollte geschlossen werden! Glücklicherweise bietet uns die Web Animations API seit Chromium 39 die Möglichkeit, Animationen abzuspielen, anzuhalten und umzukehren.

Sie können die Animation oben aufnehmen und eine sanfte, umgekehrte Animation erstellen, wenn Sie mit .reverse() noch einmal auf die Schaltfläche klicken. Auf diese Weise können Sie eine reibungslosere und kontextbezogenere Interaktion für unser modales Fenster erstellen.

Beispiel für ein modales Fenster, das beim Klicken auf eine Schaltfläche geöffnet und geschlossen wird. Demo zu Glitch ansehen

Sie können einfach zwei Animationen mit ausstehender Wiedergabe (openModal und eine Inline-Deckkrafttransformation) erstellen und dann eine der Animationen pausieren, bis die andere abgeschlossen ist. Anschließend kannst du mit Promis warten, bis ein Spiel beendet ist, bevor du es spielst. Schließlich können Sie überprüfen, ob ein Flag gesetzt ist, und dann jede Animation umkehren.

Beispiel: Dynamische Interaktionen mit partiellen Keyframes

Retargeting-Beispiel, bei dem die Animation durch einen Mausklick an eine neue Position angepasst wird. Demo zu Glitch ansehen
selector.animate([{transform: `translate(${x}px, ${y}px)`}],
    {duration: 1000, fill: 'forwards'});

In diesem Beispiel gibt es nur einen Keyframe und keine Startposition. Dies ist ein Beispiel für die Verwendung von Teil-Keyframes. Der Maus-Handler führt hier einige Schritte aus: Er legt eine neue Endposition fest und löst eine neue Animation aus. Die neue Startposition wird aus der aktuellen zugrunde liegenden Position abgeleitet.

Neue Übergänge können ausgelöst werden, solange vorhandene noch ausgeführt werden. Das bedeutet, dass der aktuelle Übergang unterbrochen und ein neuer erstellt wird.

Leistungsverbesserungen durch austauschbare Animationen

Beim Erstellen von Animationen, die auf Ereignissen basieren (z. B. auf 'mousemove'), wird jedes Mal eine neue Animation erstellt. Dies kann schnell Arbeitsspeicher belegen und die Leistung beeinträchtigen. Um dieses Problem zu beheben, wurden in Chromium 83 austauschbare Animationen eingeführt, die eine automatische Bereinigung ermöglichen. Fertige Animationen werden als austauschbar markiert und automatisch entfernt, wenn sie durch eine andere abgeschlossene Animation ersetzt werden. Dazu ein Beispiel:

Eine Kometenspur wird animiert, wenn sich die Maus bewegt. Demo zu Glitch ansehen
elem.addEventListener('mousemove', evt => {
  rectangle.animate(
    { transform: translate(${evt.clientX}px, ${evt.clientY}px) },
    { duration: 500, fill: 'forwards' }
  );
});

Jedes Mal, wenn die Maus bewegt wird, berechnet der Browser die Position jeder Kugel auf der Kometenspur neu und erstellt eine Animation bis zu diesem neuen Punkt. Der Browser weiß jetzt, dass alte Animationen entfernt und dadurch ersetzt werden können, wenn:

  1. Die Animation ist beendet.
  2. In der zusammengesetzten Reihenfolge befinden sich eine oder mehrere Animationen weiter oben, die ebenfalls fertig sind.
  3. Bei den neuen Animationen werden dieselben Eigenschaften animiert.

Sie können genau sehen, wie viele Animationen ersetzt werden, indem Sie für jede entfernte Animation einen Zähler zählen und den Zähler über anim.onremove auslösen.

Es gibt einige zusätzliche Methoden, um die Animationssteuerung noch weiter zu optimieren:

  • Mit animation.replaceState() wird erfasst, ob eine Animation aktiv, beibehalten oder entfernt ist.
  • animation.commitStyles() aktualisiert den Stil eines Elements basierend auf dem zugrunde liegenden Stil zusammen mit allen Animationen für das Element in der zusammengesetzten Reihenfolge.
  • animation.persist() markiert eine Animation als nicht austauschbar.

Flüssigere Animationen dank zusammengesetzter Modi

Mit der Web Animations API können Sie jetzt den zusammengesetzten Modus Ihrer Animationen festlegen, d. h. neben dem Standardmodus "Ersetzen" additiv oder akkumulierend sein können. Mit Komposit-Modi können Entwickler individuelle Animationen schreiben und steuern, wie Effekte kombiniert werden. Es werden jetzt drei zusammengesetzte Modi unterstützt: 'replace' (Standardmodus), 'add' und 'accumulate'.

Wenn Sie Animationen erstellen, können Entwickler kurze, unterschiedliche Effekte schreiben und diese miteinander kombinieren. Im folgenden Beispiel wird auf jedes Feld ein Keyframe für Drehung und Skalierung angewendet, wobei die einzige Anpassung der zusammengesetzte Modus ist, der als Option hinzugefügt wurde:

Eine Demo, die die zusammengesetzten Standard-, Add- und Akkumulationsmodi zeigt. Demo zu Glitch ansehen

Im standardmäßigen zusammengesetzten 'replace'-Modus ersetzt die abschließende Animation die Transformationseigenschaft und endet am rotate(360deg) scale(1.4). Bei 'add' addiert composite die Rotation und multipliziert die Skalierung, was den endgültigen Zustand rotate(720deg) scale(1.96) ergibt. 'accumulate' kombiniert die Transformationen, sodass rotate(720deg) scale(1.8) entsteht. Weitere Informationen zu den Feinheiten dieser zusammengesetzten Modi finden Sie in den Aufzählungen The CompositeOperation and CompositeOperationOrAuto aus der Web Animations-Spezifikation.

Sehen wir uns ein Beispiel für ein UI-Element an:

Ein hüpfendes Drop-down-Menü, auf das zwei zusammengesetzte Animationen angewendet werden. Demo zu Glitch ansehen

Hier werden zwei top-Animationen zusammengesetzt. Die erste ist eine Makro-Animation, bei der das Dropdown-Menü um die volle Höhe des Menüs selbst verschoben wird, und zwar als Slide-in-Effekt vom oberen Rand der Seite, und die zweite, eine Mikro-Animation, sorgt für einen leichten Sprung, wenn es den unteren Rand erreicht. Der zusammengesetzte Modus 'add' ermöglicht einen flüssigeren Übergang.

const dropDown = menu.animate(
    [
      { top: `${-menuHeight}px`, easing: 'ease-in' },
      { top: 0 }
    ], { duration: 300, fill: 'forwards' });

  dropDown.finished.then(() => {
    const bounce = menu.animate(
      [
        { top: '0px', easing: 'ease-in' },
        { top: '10px', easing: 'ease-out' },
        { ... }
      ], { duration: 300, composite: 'add' });
  });

Wie geht es mit der Web Animations API weiter?

Das sind alles interessante Ergänzungen der Animationsfunktionen der heutigen Browser und in Zukunft werden noch weitere Neuerungen folgen. Sehen Sie sich die folgenden zukünftigen Spezifikationen an, um zu erfahren, was als Nächstes kommt: