web-dev-qa-db-fra.com

Javascript - Comment détecter si le document a été chargé (IE 7 / Firefox 3)

Je souhaite appeler une fonction après le chargement d'un document, mais le chargement du document est peut-être terminé ou non. Si cela s'est chargé, je peux simplement appeler la fonction. S'il ne s'est PAS chargé, je peux alors attacher un écouteur d'événement. Je ne peux pas ajouter d'événementlistener après que le logiciel Onload a été déclenché car il ne sera pas appelé. Alors, comment puis-je vérifier si le document a été chargé? J'ai essayé le code ci-dessous mais cela ne fonctionne pas entièrement. Des idées?

var body = document.getElementsByTagName('BODY')[0];
// CONDITION DOES NOT WORK
if (body && body.readyState == 'loaded') {
    DoStuffFunction();
} else {
    // CODE BELOW WORKS
    if (window.addEventListener) {  
        window.addEventListener('load', DoStuffFunction, false);
    } else {
        window.attachEvent('onload', DoStuffFunction);
    }
}
154
Marcos

Tous les codes mentionnés par les galambalazs ne sont pas nécessaires. Pour faire cela en JavaScript pur, il suffit de tester document.readyState:

if (document.readyState === "complete") { init(); }

C'est aussi comme ça que jQuery le fait.

Selon l'endroit où le JavaScript est chargé, cela peut être fait à l'intérieur d'un intervalle:

var readyStateCheckInterval = setInterval(function() {
    if (document.readyState === "complete") {
        clearInterval(readyStateCheckInterval);
        init();
    }
}, 10);

En fait, document.readyState peut avoir trois états:

Retourne "chargement" pendant le chargement du document, "interactif" une fois l'analyse terminée mais toujours en train de charger des sous-ressources, et "complet" une fois chargé. - document.readyState sur le réseau de développeurs Mozilla

Donc, si vous avez seulement besoin que le DOM soit prêt, vérifiez document.readyState === "interactive". Si vous souhaitez que toute la page soit prête, y compris les images, recherchez document.readyState === "complete".

243
laurent

Pas besoin de bibliothèque. jQuery a utilisé ce script pendant un moment, au fait.

http://dean.edwards.name/weblog/2006/06/again/

// Dean Edwards/Matthias Miller/John Resig

function init() {
  // quit if this function has already been called
  if (arguments.callee.done) return;

  // flag this function so we don't do the same thing twice
  arguments.callee.done = true;

  // kill the timer
  if (_timer) clearInterval(_timer);

  // do stuff
};

/* for Mozilla/Opera9 */
if (document.addEventListener) {
  document.addEventListener("DOMContentLoaded", init, false);
}

/* for Internet Explorer */
/*@cc_on @*/
/*@if (@_win32)
  document.write("<script id=__ie_onload defer src=javascript:void(0)><\/script>");
  var script = document.getElementById("__ie_onload");
  script.onreadystatechange = function() {
    if (this.readyState == "complete") {
      init(); // call the onload handler
    }
  };
/*@end @*/

/* for Safari */
if (/WebKit/i.test(navigator.userAgent)) { // sniff
  var _timer = setInterval(function() {
    if (/loaded|complete/.test(document.readyState)) {
      init(); // call the onload handler
    }
  }, 10);
}

/* for other browsers */
window.onload = init;
32
gblazex

Vous voudrez probablement utiliser quelque chose comme jQuery, ce qui facilite la programmation JS.

Quelque chose comme:

$(document).ready(function(){
   // Your code here
});

Semblerait faire ce que vous êtes après.

15
dan

Si vous voulez réellement que ce code fonctionne à load, pas à domready (c’est-à-dire que vous devez également charger les images), alors malheureusement, la fonction Ready ne le fait pas pour vous. Je fais généralement juste quelque chose comme ça:

Inclure dans le document javascript (c'est-à-dire toujours appelé avant que le chargement en charge ne soit déclenché):

var pageisloaded=0;
window.addEvent('load',function(){
 pageisloaded=1;
});

Puis votre code:

if (pageisloaded) {
 DoStuffFunction();
} else {
 window.addEvent('load',DoStuffFunction);
}

(Ou l'équivalent dans votre cadre de préférence.) J'utilise ce code pour faire du précaching de javascript et d'images pour les pages futures. Étant donné que les éléments que je récupère ne sont pas du tout utilisés pour cette page, je ne souhaite pas qu’ils aient la priorité sur le téléchargement rapide des images.

Il y a peut-être un meilleur moyen, mais je ne l'ai pas encore trouvé.

5
Nathan Stretch
if(document.readyState === 'complete') {
    DoStuffFunction();
} else {
    if (window.addEventListener) {  
        window.addEventListener('load', DoStuffFunction, false);
    } else {
        window.attachEvent('onload', DoStuffFunction);
    }
}
5
Jman

Mozila Firefox dit que onreadystatechange est une alternative à DOMContentLoaded.

// alternative to DOMContentLoaded
document.onreadystatechange = function () {
    if (document.readyState == "complete") {
        initApplication();
    }
}

Dans DOMContentLoaded le doc de Mozila dit:

L'événement DOMContentLoaded est déclenché lorsque le document a été complètement chargé et analysé, sans attendre que les feuilles de style, les images et les sous-trames soient complètement chargés (l'événement load peut être utilisé pour détecter une page entièrement chargée).

Je pense que l'événement load devrait être utilisé pour un chargement complet du document + des ressources.

3
Mostafa Talebi

Celui ci-dessus avec JQuery est le moyen le plus simple et le plus utilisé. Cependant, vous pouvez utiliser du javascript pur, mais essayez de définir ce script dans la tête afin qu’il soit lu au début. Ce que vous recherchez, c'est l'événement window.onload.

Voici un script simple que j'ai créé pour exécuter un compteur. Le compteur s’arrête ensuite après 10 itérations

window.onload=function()
{
    var counter = 0;
    var interval1 = setInterval(function()
    { 
        document.getElementById("div1").textContent=counter;
        counter++; 
        if(counter==10)
        {
            clearInterval(interval1);
        }
    },1000);

}
3
Talha

Essaye ça:

var body = document.getElementsByTagName('BODY')[0];
// CONDITION DOES NOT WORK
if ((body && body.readyState == 'loaded') || (body &&  body.readyState == 'complete') ) {
    DoStuffFunction();
} else {
    // CODE BELOW WORKS
    if (window.addEventListener) {
        window.addEventListener('load', DoStuffFunction, false);
    } else {
        window.attachEvent('onload',DoStuffFunction);
    }
}
2
smit

J'ai une autre solution, mon application doit être démarrée quand un nouvel objet de MyApp est créé, il ressemble donc à:

function MyApp(objId){
     this.init=function(){
        //.........
     }
     this.run=function(){
          if(!document || !document.body || !window[objId]){
              window.setTimeout(objId+".run();",100);
              return;
          }
          this.init();
     };
     this.run();
}
//and i am starting it 
var app=new MyApp('app');

cela fonctionne sur tous les navigateurs, que je sache.

1
vitus