DOMException - Die play() -Anfrage wurde unterbrochen.

François Beaufort
François Beaufort

Sind Sie in den Chrome-Entwicklertools auf diesen unerwarteten Medienfehler gestoßen? JavaScript-Konsole?

oder

Dann sind Sie hier richtig. Keine Angst. Im Folgenden erfahren Sie, was die Ursache ist und wie Sie das Problem beheben können.

Ursache

Im Folgenden finden Sie JavaScript-Code, der den Fehler "Nicht abgefangen (in Promise)" reproduziert. angezeigter Fehler:

Don'ts
<video id="video" preload="none" src="https://example.com/file.mp4"></video>

<script>
  video.play(); // <-- This is asynchronous!
  video.pause();
</script>

Der obige Code führt zu dieser Fehlermeldung in den Chrome-Entwicklertools:

_Uncaught (in promise) DOMException: The play() request was interrupted by a call to pause().

Da das Video aufgrund von preload="none" nicht geladen wurde, funktioniert die Videowiedergabe nicht unbedingt sofort nach der Ausführung von video.play() beginnen.

Seit Chrome 50 wurden außerdem play()-Aufrufe auf <video>- oder <audio>- -Element gibt ein Promise zurück, eine Funktion, die ein einzelnes Ergebnis zurückgibt. asynchron programmiert. Wenn die Wiedergabe erfolgreich ist, ist das Versprechen erfüllt playing-Ereignis wird gleichzeitig ausgelöst. Wenn die Wiedergabe fehlschlägt, abgelehnt zusammen mit einer Fehlermeldung, die den Fehler erklärt.

Folgendes passiert:

  1. video.play() beginnt mit dem asynchronen Laden des Videocontents.
  2. video.pause() unterbricht das Laden des Videos, weil es noch nicht bereit ist.
  3. video.play() lehnt asynchron ab.

Da wir das Promise-Video nicht in unserem Code verarbeiten, die in den Chrome-Entwicklertools angezeigt werden.

Lösung

Da wir nun die Ursache kennen, können wir versuchen, dieses Problem zu beheben.

Gehen Sie nie davon aus, dass ein Medienelement (Video oder Audio) wiedergegeben wird. Sieh dir Das von der Funktion play zurückgegebene Promise, um zu prüfen, ob es abgelehnt wurde. Es ist dass das Versprechen erst erfüllt wird, wenn die Wiedergabe tatsächlich abgeschlossen ist, gestartet, was bedeutet, dass der Code in then() erst ausgeführt wird, wenn die Mediendatei gerade läuft.

Do

Beispiel: Autoplay

<video id="video" preload="none" src="https://example.com/file.mp4"></video>

<script>
  // Show loading animation.
  var playPromise = video.play();

  if (playPromise !== undefined) {
    playPromise.then(_ => {
      // Automatic playback started!
      // Show playing UI.
    })
    .catch(error => {
      // Auto-play was prevented
      // Show paused UI.
    });
  }
</script>
Do

Beispiel: Play & Pausieren

<video id="video" preload="none" src="https://example.com/file.mp4"></video>
 
<script>
  // Show loading animation.
  var playPromise = video.play();
 
  if (playPromise !== undefined) {
    playPromise.then(_ => {
      // Automatic playback started!
      // Show playing UI.
      // We can now safely pause video...
      video.pause();
    })
    .catch(error => {
      // Auto-play was prevented
      // Show paused UI.
    });
  }
</script>

Das ist großartig für dieses einfache Beispiel, aber was, wenn Sie video.play() verwenden, ein Video später abspielen?

Ich verrate dir ein Geheimnis. Sie müssen video.play() nicht verwenden, video.load(). Und so geht's:

Do

Beispiel: Abrufen und Wiedergeben

<video id="video"></video>
<button id="button"></button>

<script>
  button.addEventListener('click', onButtonClick);

  function onButtonClick() {
    // This will allow us to play video later...
    video.load();
    fetchVideoAndPlay();
  }

  function fetchVideoAndPlay() {
    fetch('https://example.com/file.mp4')
    .then(response => response.blob())
    .then(blob => {
      video.srcObject = blob;
      return video.play();
    })
    .then(_ => {
      // Video playback started ;)
    })
    .catch(e => {
      // Video playback failed ;(
    })
  }
</script>

Play Promise-Support

Zum Zeitpunkt des Schreibens gibt HTMLMediaElement.play() ein Promise in Chrome, Edge, Firefox, Opera und Safari.

Gefahrenbereich

<source> innerhalb von <video> gibt play() versprechen nie ab

Für <video src="not-existing-video.mp4"\> wird das Promise play() abgelehnt als nicht erwartet, da das Video nicht existiert. Für <video><source src="not-existing-video.mp4" type='video/mp4'></video> das Versprechen von play() wird nie abgelehnt. Dies geschieht nur, wenn keine gültigen Quellen vorhanden sind.

Chromium-Programmfehler