web-dev-qa-db-fra.com

javascript domready?

Je sais que je peux utiliser différents frameworks comme prototype ou jquery pour attacher une fonction à window.onload, mais ce n'est pas ce que je recherche.

J'ai besoin de quelque chose comme .readyState pour pouvoir faire quelque chose comme ceci:

if(document.isReady){
  var id = document.getElem ...
}

y a-t-il un autre moyen que d'utiliser ce que font les frameworks?

49
kristian nissen

j'ai mis à jour le code de Bibliothèque DOMAssistant ça marche très bien avec moi 

var domReady = (function (){
  var arrDomReadyCallBacks = [] ;
  function excuteDomReadyCallBacks(){
       for (var i=0; i < arrDomReadyCallBacks.length; i++) {
         arrDomReadyCallBacks[i]();
       }
       arrDomReadyCallBacks = [] ;
  }

  return function (callback){
    arrDomReadyCallBacks.Push(callback);
     /* Mozilla, Chrome, Opera */
      if (document.addEventListener ) {
          document.addEventListener('DOMContentLoaded', excuteDomReadyCallBacks, false);
      }
    /* Safari, iCab, Konqueror */
    if (/KHTML|WebKit|iCab/i.test(navigator.userAgent)) {
        browserTypeSet = true ;
        var DOMLoadTimer = setInterval(function () {
            if (/loaded|complete/i.test(document.readyState)) {
                //callback();
                excuteDomReadyCallBacks();
                clearInterval(DOMLoadTimer);
            }
        }, 10);
    }
    /* Other web browsers */

    window.onload = excuteDomReadyCallBacks;
}
})()
8
Yehia

Edit: Alors que l'année 2018 arrive, je pense qu'il est prudent d'écouter l'événement DOMContentLoaded .

function fireOnReady() { /* ... */ }
if (document.readyState === 'complete') {
    fireOnReady();
} else {
    document.addEventListener("DOMContentLoaded", fireOnReady);
}

Veuillez noter que l'événement ne sera déclenché que une fois lors du chargement de votre page! Si vous devez prendre en charge de très vieux navigateurs, alors consultez le script super léger que j'ai mis en place ci-dessous.



Pour référence historique uniquement:



jQuery a une propriété non documentée appelée isReady qui est utilisée en interne pour déterminer si l'événement DOM ready a été déclenché:

if($.isReady) {
    // DOM is ready
} else {
    // DOM is not yet ready
}

J'ai commencé à 1.5.2 jusqu'à 1.3.2 et la propriété est là. Bien que non documentée, je dirais que vous pouvez compter sur cette propriété dans les versions futures de jQuery .Edit: Et un an plus tard - v1.7.2, ils utilisent toujours $.isReady - toujours non documenté, veuillez donc l'utiliser à votre à vos propres riques. Soyez prudent lors de la mise à niveau.

Edit: v1.9, ils utilisent toujours $.isReady - toujours non documenté

Edit: v2.0, avec toutes ses modifications "majeures", utilise toujours $.isReady - toujours non documenté

Edit: v3.x utilise toujours $.isReady - toujours non documenté

Edit: Comme plusieurs personnes l'ont souligné, ce qui précède ne répond pas vraiment à la question. Je viens donc de créer un mini fragment prêt pour DOM qui a été inspiré par Dustin Diaz même un plus petit fragment prêt pour DOM . Dustin a créé un moyen élégant de vérifier le document readyState avec quelque chose de similaire à ceci:

if( !/in/.test(document.readyState) ) {
    // document is ready
} else {
    // document is NOT ready
}

Cela fonctionne parce que le navigateur a 3 états de chargement: "chargement", "interactif" et "complet" (l'ancien WebKit utilisait aussi "chargé", mais vous n'avez plus à vous en préoccuper).. Vous remarquerez que "loading" et "interactive" contiennent le texte "in" ... donc si la chaîne "in" se trouve à l'intérieur de document.readyState, nous savons que nous ne sommes pas encore prêts.

40
Ryan Wheale

Bien que je préconise généralement d’éviter d’utiliser des cadres sauf si nécessaire, je dirais qu’en utiliser un dans ce cas est tout à fait acceptable. Voici jQuery:

$(function () {
    // do stuff after DOM has loaded
});

Notez que ce n'est PAS la même chose qu'un événement window.onload, puisque onload est exécuté en premier après le chargement d'autres ressources (images, etc.). Le code que j'ai utilisé dans mon exemple sera exécuté lorsque le DOM aura fini de se charger, c'est-à-dire lorsque la structure HTML complète est disponible (pas nécessairement lorsque les images, CSS, etc. sont disponibles.)

Si vous voulez une variable vérifiable, vous pouvez en définir une dans la fonction ready:

var documentIsReady = false;
$(function () { documentIsReady = true; });

Bien sûr, vous pouvez trouver encore plus de bibliothèques plus légères que jQuery si tout ce que vous voulez faire est de vérifier si elles sont prêtes pour le DOM. Mais utilisez une bibliothèque dans les cas où différents navigateurs se comportent de manière très différente (c'est un cas de ce type).

En utilisant du code de la bibliothèque DOMAssistant , créer votre propre fonction "DOM est prêt" ne devrait pas être trop difficile:

var domLoaded = function (callback) {
    /* Internet Explorer */
    /*@cc_on
    @if (@_win32 || @_win64)
        document.write('<script id="ieScriptLoad" defer src="//:"><\/script>');
        document.getElementById('ieScriptLoad').onreadystatechange = function() {
            if (this.readyState == 'complete') {
                callback();
            }
        };
    @end @*/
    /* Mozilla, Chrome, Opera */
    if (document.addEventListener) {
        document.addEventListener('DOMContentLoaded', callback, false);
    }
    /* Safari, iCab, Konqueror */
    if (/KHTML|WebKit|iCab/i.test(navigator.userAgent)) {
        var DOMLoadTimer = setInterval(function () {
            if (/loaded|complete/i.test(document.readyState)) {
                callback();
                clearInterval(DOMLoadTimer);
            }
        }, 10);
    }
    /* Other web browsers */
    window.onload = callback;
};

Pas testé, mais ça devrait marcher. Je l'ai simplifiée à partir de DOMAssistant, car DOMAssistant autorise plusieurs rappels et vérifie que vous ne pouvez pas ajouter deux fois la même fonction, etc.

32
Blixt

Au cours des cinq années écoulées depuis que cette question a été posée, DOMContentLoaded est devenu un événement universellement pris en charge, et vous pouvez simplement l'utiliser.

document.addEventListener('DOMContentLoaded', function() {
    //.. do stuff ..
}, false);
29
Damon Smith

Découvrez cette démo de Microsoft. -> http://www.microsoft.com/testdrive/HTML5/DOMContentLoaded/Default.html Voici le résumé du code qui vous permet d'exécuter JS sur DOM prêt ...

(function () {
    function load2(){
        // put whatever you need to load on DOM ready in here
        document.getElementById("but3").addEventListener("click", doMore, false);
    }
    if (window.addEventListener) {
        window.addEventListener('DOMContentLoaded', load2, false);
    } else {
        window.attachEvent('onload', load2);
    }
} ());

Voici quelques sources javascript pour la démo .. http://ie.Microsoft.com/testdrive/Includes/Script/ReturnAndShareControls.js

Ça marche bien. Nice !! .. sur Google Chrome et IE 9.

10
Randy Skretka
document.addEventListener("DOMContentLoaded", function(e){
    console.log("dom ready");//output to web browser console
});

jQuery n'est pas nécessaire pour cela. Il n'est pas nécessaire de passer le 3ème paramètre sur un DOMContentLoaded car cet événement n'a pas de parent pour parcourir l'événement. En outre, pas besoin d'avoir toute la fantaisie avec ce que tout le monde dit. Cela vous indiquera quand le DOM est complètement chargé et prêt à être utilisé. J'ai LOLED quand j'ai remarqué l'assistant DOM, lib. Cette lib est absolument inutile. 

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-images aient fini de se charger.

addEventListener() est une excellente fonction pour vérifier tout événement, y compris le statut Prêt pour le DOM. Lorsque vous utilisez "DOMContentLoaded", le troisième paramètre de addEventListener() n'est pas nécessaire, car ce déclencheur n'a pas d'élément parent pour transmettre également l'événement. Dans mon exemple ci-dessus, vous remarquerez que le deuxième paramètre est une fonction anonyme. Vous pouvez également passer le nom d'une fonction dans le deuxième paramètre. 

document.addEventListener([(string)event trigger], [function],[(boolean)traverse DOM tree]);

Un autre avantage à utiliser ceci sur JQuery est que cela ne se cassera pas lorsque vous mettrez à jour JQuery. 

8
Patrick W. McMahon

jQuery n'utilise pas window.onload.

$(document).ready() attend que le DOM soit chargé et puisse être parcouru (le reste du contenu peut être chargé ou non par ce point).

Si vous extrayez le code source de jQuery et triez le désordre, vous constaterez que le travail est effectué à l'aide de la méthode bindReady(), qui comporte plusieurs implémentations différentes pour différents navigateurs. événement de chargement pour la fenêtre.

6
Justin Niessner

C’est en fait l’une des principales raisons pour lesquelles la plupart des gens utilisent des frameworks tels que jQuery car la solution à ce problème n’est pas cohérente d’un navigateur à l’autre.

3
Scott Fox

Essaye ça:
Lien: onDomReady sur GitHub Ou la source ci-dessous:

if(document.ondomready == undefined) {
    document.ondomready = {};
    document.ondomready = null;
} else {
    document.ondomready=document.ondomready;
}
var oldonload=document.onload;
var isLaunched = 0;
document.onload = function() {  
    if(oldonload !== null) {
        oldonload.call();
    }
};
document.addEventListener("DOMContentLoaded", function onDom(evt) {
    var olddomready = document.ondomready;
    if(olddomready !== null) {
        if(isLaunched == 0) {
            olddomready.call(evt);
            isLaunched == 1;
            //We now launched the mapped DOMContentLoaded Event
        } else {
            //We already launched DOMContentLoaded Event
        }
    }
}, false);

J'ai déjà testé cela sur Opera 11.x/12.x. Pas encore testé sur d'autres. Faites-moi savoir s'ils le font.

Remarque: Je n'ai pas encore téléchargé le référentiel, mais je le ferai bientôt pendant mon temps libre.

1
dsrdakota

Si vous voulez des bibliothèques plus petites qui ne font que des choses particulières, vous pouvez utiliser des bibliothèques dans microjs . Pour la question en cause, la méthode DOMStatic libs ready peut être utilisée. 

0
Jerome Anthony