En mi expectativa, deseo usar MutationObserver para escuchar el evento que indica que el video se ha cargado. El motivo es que necesito agregar una animación de carga antes de que el video se haya renderizado y cargado en el DOM, luego elimino la animación cuando el video se muestra en la página. Parece que MutationObserver no pudo decir la hora en que se cargó el video, solo sabe que los atributos cambiaron.
A continuación se muestra mi código:
const callback = () => { console.log('done') } const observer = new MutationObserver(callback) this.observer.observe(videoNode, { attributes: true })En mi expectativa, deseo usar
MutationObserverpara escuchar el evento que indica que el video se ha cargado. El motivo es que necesito agregar una animación de carga antes de que el video se haya renderizado y cargado en el DOM, luego elimino la animación cuando el video se muestra en la página. Parece queMutationObserverno pudo decir la hora en que se cargó el video, solo sabe que los atributos cambiaron. a continuación es mi código.
¿Por qué es MutationObserver para esto cuando HTMLVideoElement ya tiene un evento de load y propiedades readyState que le brindan esta información exacta? (Aunque probablemente debería usar canplay o los eventos de loadeddata en lugar de load ).
El uso de MutationObserver no funcionará de todos modos porque es para observar cambios estructurales en el árbol DOM (por ejemplo, agregar/eliminar elementos y atributos, pero no propiedades de objetos), por lo que no observará cambios en las propiedades DOM que son independientes de los atributos DOM (como los atributos de los elementos no se asignan 1:1 a las propiedades del objeto, esto también se aplica a CSS: puede configurar disabled en HTMLInputElement y la psuedo-clase :disabled funcionará, pero no coincidirá con el selector de atributo [disabled] ).
Todo lo que necesitas es esto:
// https://developer.mozilla.org/en-US/docs/Web/API/HTMLMediaElement/readyState const READYSTATE_HAVE_NOTHING = 0; const READYSTATE_HAVE_METADATA = 1; const READYSTATE_HAVE_CURRENT_DATA = 2; const READYSTATE_HAVE_FUTURE_DATA = 3; const READYSTATE_HAVE_ENOUGH_DATA = 4; const videoElement = document.querySelector( 'video#someId' ); if( !videoElement ) throw new Error( "Couldn't find <video> element." ); if( videoElement.readyState === READYSTATE_HAVE_ENOUGH_DATA ) { // If the video is already loaded, don't do anything. } else { // Else, show the spinner and remove it after it's loaded: const spinner = document.createElement('div'); spinner.classList.add('spinner'); videoElement.parent.appendChild( spinner ); videoElement.addEventListener( 'canplay', function() { document.querySelector('.spinner')?.remove(); } ); }