Signatur
Beschreibung
Das cancel-Ereignis der Animation-Schnittstelle (Web Animations API) wird ausgelöst, wenn eine laufende, pausierte oder beendete Animation in den Wiedergabestatus "idle" wechselt. Das passiert typischerweise durch einen Aufruf von Animation.cancel(), aber auch indirekt, etwa wenn ein Element mit einer CSS-Animation aus dem Dokument entfernt oder auf display: none gesetzt wird oder wenn eine CSS-Animation durch Entfernen der animation-name-Eigenschaft beendet wird.
Sie registrieren den Handler entweder mit animation.addEventListener("cancel", handler) oder über die Eigenschaft animation.oncancel = handler. Der Handler erhält ein AnimationPlaybackEvent mit den Eigenschaften currentTime (beim Abbruch immer null) und timelineTime.
Praktisch ist das Ereignis, um Aufräumarbeiten durchzuführen, wenn eine Animation nicht regulär endet: zum Beispiel Zustände zurücksetzen, Klassen entfernen, Ressourcen freigeben oder ein wartendes Promise zu verwerfen. Im Gegensatz zu finish signalisiert cancel einen Abbruch – alle Effekte der Animation werden entfernt, das Element kehrt in seinen ursprünglichen Stil zurück.
Das Ereignis wird nicht ausgelöst, wenn die Animation bereits im Status "idle" ist. Es wird asynchron (als Task/Mikro-Zeitpunkt im Animations-Update) dispatcht, nicht synchron innerhalb von cancel().
Parameter
| Name | Typ | Default | Beschreibung |
|---|---|---|---|
| $type Pflicht | string | Der Ereignisname "cancel". |
|
| $handler Pflicht | (event: AnimationPlaybackEvent) => void | Callback, der beim Abbruch aufgerufen wird. Erhält ein AnimationPlaybackEvent mit currentTime (null) und timelineTime. |
|
| $options | boolean | AddEventListenerOptions | false | Optionale Listener-Optionen wie { once: true } oder { signal }. |
Rückgabewert
addEventListener gibt nichts zurück. Der Handler erhält ein AnimationPlaybackEvent.Beispiele
Abbruch mit addEventListener erkennen
const box = document.querySelector('.box');
const anim = box.animate(
[{ transform: 'translateX(0)' }, { transform: 'translateX(300px)' }],
{ duration: 2000, fill: 'forwards' }
);
anim.addEventListener('cancel', (event) => {
console.log('Animation abgebrochen', event.currentTime, anim.playState);
});
// Nach 500 ms abbrechen
setTimeout(() => anim.cancel(), 500);
oncancel-Eigenschaft und Listener wieder entfernen
const el = document.querySelector('#spinner');
const anim = el.animate([{ rotate: '0deg' }, { rotate: '360deg' }], {
duration: 1000,
iterations: Infinity
});
const onCancel = () => {
el.classList.remove('loading');
console.log('Spinner gestoppt');
};
// Variante 1: on-Property
anim.oncancel = onCancel;
// Variante 2: Listener registrieren und später wieder entfernen
anim.addEventListener('cancel', onCancel);
anim.removeEventListener('cancel', onCancel);
document.querySelector('#stop').addEventListener('click', () => anim.cancel());
Animation als Promise mit Abbruch-Behandlung
const animateAsync = (el, keyframes, options) =>
new Promise((resolve, reject) => {
const anim = el.animate(keyframes, options);
anim.addEventListener('finish', () => resolve(anim), { once: true });
anim.addEventListener('cancel', () => reject(new Error('abgebrochen')), { once: true });
});
const panel = document.querySelector('.panel');
try {
await animateAsync(panel, [{ opacity: 0 }, { opacity: 1 }], { duration: 400 });
console.log('Eingeblendet');
} catch (err) {
console.log('Einblenden', err.message);
}
CSS-Animation wird durch display:none abgebrochen
const toast = document.querySelector('.toast'); // hat eine CSS-Animation
const [cssAnim] = toast.getAnimations();
cssAnim?.addEventListener('cancel', () => {
console.log('CSS-Animation abgebrochen');
});
toast.style.display = 'none';
// Wichtig · Fallstricke
- Nicht mit
finishverwechseln:cancelfeuert nur beim Abbruch; eine regulär beendete Animation löstfinishaus. Wer beide Fälle behandeln will, muss beide Ereignisse abonnieren. - Das Ereignis wird nicht erneut ausgelöst, wenn
cancel()auf einer bereits inaktiven Animation (playState === "idle") aufgerufen wird. - Nach einem Abbruch wird das
finished-Promise mit einemAbortError(DOMException) verworfen – unbehandelt führt das zu „Unhandled Promise Rejection“-Warnungen. Ggf.anim.finished.catch(() => {})anhängen. - Die Zustellung ist asynchron; Code direkt nach
anim.cancel()läuft vor dem Handler. - Bei CSS-Animationen und -Transitions ist das Ereignis auch über
animationcancelbzw.transitioncancelam Element verfügbar. - Kompatibilität: in Chrome/Edge 84+, Firefox 48+ und Safari 13.1+ unterstützt; sehr alte Browser benötigen ggf. das Web-Animations-Polyfill.